From 6519b97edaf9a5eae6dbc753d65d15893d4f739d Mon Sep 17 00:00:00 2001 From: Matt Madia Date: Sun, 20 Jan 2013 17:50:03 -0500 Subject: [PATCH 01/86] Fixed a typo. --- src/add-ons/kernel/drivers/audio/ice1712/multi.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/add-ons/kernel/drivers/audio/ice1712/multi.c b/src/add-ons/kernel/drivers/audio/ice1712/multi.c index 9867e9bc1d..745315f89b 100644 --- a/src/add-ons/kernel/drivers/audio/ice1712/multi.c +++ b/src/add-ons/kernel/drivers/audio/ice1712/multi.c @@ -145,7 +145,7 @@ ice1712_get_description(ice1712 *card, multi_description *data) break; } - strncpy(data->vendor_info, "Haiku OS", 32); + strncpy(data->vendor_info, "Haiku", 32); data->output_channel_count = card->total_output_channels; data->input_channel_count = card->total_input_channels; From 06437987e0813e4405d56462ebca86fdb9d84d9f Mon Sep 17 00:00:00 2001 From: Matt Madia Date: Sun, 20 Jan 2013 17:53:50 -0500 Subject: [PATCH 02/86] Corrected the name of the operating system. Automatic whitespace cleanup too. No functional changes. --- .../kernel/busses/scsi/usb/device_info.h | 32 +-- .../kernel/busses/scsi/usb/fake_device.c | 20 +- .../kernel/busses/scsi/usb/fake_device.h | 10 +- .../kernel/busses/scsi/usb/proto_bulk.c | 56 ++-- .../kernel/busses/scsi/usb/proto_bulk.h | 16 +- .../kernel/busses/scsi/usb/proto_cbi.c | 46 ++-- .../kernel/busses/scsi/usb/proto_cbi.h | 18 +- .../kernel/busses/scsi/usb/proto_common.c | 38 +-- .../kernel/busses/scsi/usb/proto_common.h | 14 +- .../kernel/busses/scsi/usb/proto_module.h | 28 +- src/add-ons/kernel/busses/scsi/usb/settings.c | 100 ++++---- src/add-ons/kernel/busses/scsi/usb/settings.h | 14 +- .../kernel/busses/scsi/usb/sg_buffer.c | 18 +- .../kernel/busses/scsi/usb/sg_buffer.h | 14 +- src/add-ons/kernel/busses/scsi/usb/tracing.c | 44 ++-- src/add-ons/kernel/busses/scsi/usb/tracing.h | 22 +- .../kernel/busses/scsi/usb/transform_procs.h | 16 +- src/add-ons/kernel/busses/scsi/usb/usb_defs.h | 18 +- src/add-ons/kernel/busses/scsi/usb/usb_scsi.c | 240 +++++++++--------- src/add-ons/kernel/busses/scsi/usb/usb_scsi.h | 16 +- 20 files changed, 390 insertions(+), 390 deletions(-) diff --git a/src/add-ons/kernel/busses/scsi/usb/device_info.h b/src/add-ons/kernel/busses/scsi/usb/device_info.h index 6f917fd764..3b5c9d2b96 100644 --- a/src/add-ons/kernel/busses/scsi/usb/device_info.h +++ b/src/add-ons/kernel/busses/scsi/usb/device_info.h @@ -1,55 +1,55 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ -#ifndef _DEVICE_INFO_H_ +#ifndef _DEVICE_INFO_H_ #define _DEVICE_INFO_H_ #ifndef _SCSI_COMMANDS_H_ #include "scsi_commands.h" -#endif /*_SCSI_COMMANDS_H_*/ +#endif /*_SCSI_COMMANDS_H_*/ -#ifndef _PROTO_MODULE_H_ +#ifndef _PROTO_MODULE_H_ #include "proto_module.h" -#endif /* _PROTO_MODULE_H_ */ +#endif /* _PROTO_MODULE_H_ */ typedef struct _usb_device_info{ uint8 dev_num; /**/ const usb_device device; /**/ uint16 interface; /**/ uint8 max_lun; /**/ - + uint32 properties; - + usb_pipe pipe_in; /**/ usb_pipe pipe_out; /**/ usb_pipe pipe_intr; /**/ - + sem_id lock_sem; /**/ sem_id trans_sem; /**/ uint32 tag; /**/ status_t status; /**/ - + bigtime_t trans_timeout; usb_module_info *usb_m; - + void *data; /**/ int actual_len; /**/ - + protocol_module_info *protocol_m; char *protocol_m_path; - + transform_module_info *transform_m; char *transform_m_path; - + bool b_trace; void (*trace)(bool b_force, const char *fmt, ...); void (*trace_bytes)(const char *prefix, const uint8 *bytes, size_t bytes_len); diff --git a/src/add-ons/kernel/busses/scsi/usb/fake_device.c b/src/add-ons/kernel/busses/scsi/usb/fake_device.c index e20ade153e..d49e7b160d 100644 --- a/src/add-ons/kernel/busses/scsi/usb/fake_device.c +++ b/src/add-ons/kernel/busses/scsi/usb/fake_device.c @@ -1,20 +1,20 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ -#include "usb_scsi.h" +#include "usb_scsi.h" #include -#include "device_info.h" -#include "tracing.h" +#include "device_info.h" +#include "tracing.h" #include "fake_device.h" @@ -38,7 +38,7 @@ void fake_inquiry_request(usb_device_info *udi, CCB_SCSIIO *ccbio) if(ccbio->cam_dxfer_len >= 0x24){ strncpy(&data[8], "USB SCSI", INQ_VENDOR_LEN); strncpy(&data[16], "Reserved", INQ_PRODUCT_LEN); - strncpy(&data[32], "N/A", INQ_REVISION_LEN); + strncpy(&data[32], "N/A", INQ_REVISION_LEN); } } } @@ -62,8 +62,8 @@ void fake_test_unit_ready_request(CCB_SCSIIO *ccbio) \fn:fake_scsi_io \param ccbio: ???? \return: ??? - - xpt_scsi_io - handle XPT_SCSI_IO sim action + + xpt_scsi_io - handle XPT_SCSI_IO sim action */ status_t fake_scsi_io(CCB_SCSIIO *ccbio) { diff --git a/src/add-ons/kernel/busses/scsi/usb/fake_device.h b/src/add-ons/kernel/busses/scsi/usb/fake_device.h index ea89ac8e19..571e5017a8 100644 --- a/src/add-ons/kernel/busses/scsi/usb/fake_device.h +++ b/src/add-ons/kernel/busses/scsi/usb/fake_device.h @@ -1,16 +1,16 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ -#ifndef _FAKE_DEVICE_H_ +#ifndef _FAKE_DEVICE_H_ #define _FAKE_DEVICE_H_ void fake_inquiry_request(usb_device_info *udi, CCB_SCSIIO *ccbio); diff --git a/src/add-ons/kernel/busses/scsi/usb/proto_bulk.c b/src/add-ons/kernel/busses/scsi/usb/proto_bulk.c index cec9ad9a83..c369152a29 100644 --- a/src/add-ons/kernel/busses/scsi/usb/proto_bulk.c +++ b/src/add-ons/kernel/busses/scsi/usb/proto_bulk.c @@ -1,14 +1,14 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** bulk-only protocol specific implementation */ @@ -17,15 +17,15 @@ * http://www.usb.org/developers/data/devclass/usbmassover_11.pdf [1] * http://www.usb.org/developers/data/devclass/usbmassbulk_10.pdf [2] */ -#include "usb_scsi.h" +#include "usb_scsi.h" -#include "device_info.h" +#include "device_info.h" -#include "proto_module.h" -#include "proto_common.h" -#include "proto_bulk.h" +#include "proto_module.h" +#include "proto_common.h" +#include "proto_bulk.h" -#include "usb_defs.h" +#include "usb_defs.h" #include /* strncpy */ @@ -83,7 +83,7 @@ void trace_CBW(usb_device_info *udi, const usb_mass_CBW *cbw) PTRACE(udi, "\nCBW:{'%s'; tag:%d; data_len:%d; flags:0x%02x; lun:%d; cdb_len:%d;}\n", buf, cbw->tag, cbw->data_transfer_len, cbw->flags, cbw->lun, cbw->cdb_len); - udi->trace_bytes("CDB:\n", cbw->CDB, CBW_CDB_LENGTH); + udi->trace_bytes("CDB:\n", cbw->CDB, CBW_CDB_LENGTH); } void trace_CSW(usb_device_info *udi, const usb_mass_CSW *csw) @@ -97,8 +97,8 @@ void trace_CSW(usb_device_info *udi, const usb_mass_CSW *csw) /** \fn:get_max_luns \param udi: device for wich max LUN info is requested - \return:always B_OK - if info was not retrieved max LUN is defaulted to 0 - + \return:always B_OK - if info was not retrieved max LUN is defaulted to 0 + tries to retrieve the maximal Logical Unit Number supported by this device. If device doesn't support GET_MAX_LUN request - single LUN is assumed. ([2] 3.2) @@ -123,7 +123,7 @@ get_max_luns(usb_device_info *udi) "Assuming single LUN available.\n", udi->dev_num, status); } udi->max_lun = 0; - status = B_OK; + status = B_OK; } /* else - all is OK - max luns info readed */ } return status; @@ -135,7 +135,7 @@ get_max_luns(usb_device_info *udi) \param len: length of data buffer \param b_in: is "true" if input (device->host) data transfer, "false" otherwise \return: status of operation. - + performs queue_bulk USB request for corresponding pipe and handle timeout of this operation. */ @@ -159,10 +159,10 @@ queue_bulk(usb_device_info *udi, void* buffer, size_t len, bool b_in) /** \fn:check_CSW \param udi:corresponding device info - \param csw: CSW to be checked for validity and meaningfullness + \param csw: CSW to be checked for validity and meaningfullness \param transfer_len: data transferred during operation, which is checked for status \return: "true" if CSW valid and meanigfull, "false" otherwise - + checks CSW for validity and meaningfullness as required by USB mass strorge BulkOnly specification ([2] 6.3) */ @@ -199,7 +199,7 @@ check_CSW(usb_device_info *udi, usb_mass_CSW* csw, int transfer_len) break;/* failed */ } is_valid = true; - }while(false); + }while(false); return is_valid; } /** @@ -208,7 +208,7 @@ check_CSW(usb_device_info *udi, usb_mass_CSW* csw, int transfer_len) \param csw: buffer for CSW data \param transfer_len: data transferred during operation, which is checked for status \return: success status code - + reads CSW from device as proposed in ([2] 5.3.3; Figure 2.). */ static status_t @@ -216,8 +216,8 @@ read_status(usb_device_info *udi, usb_mass_CSW* csw, int transfer_len) { status_t status = B_ERROR; int try = 0; - do{ - status = queue_bulk(udi, csw, CSW_LENGTH, true); + do{ + status = queue_bulk(udi, csw, CSW_LENGTH, true); if(0 == try){ if(B_OK != status || B_OK != udi->status){ status = (*udi->usb_m->clear_feature)(udi->pipe_in, USB_FEATURE_ENDPOINT_HALT); @@ -243,7 +243,7 @@ read_status(usb_device_info *udi, usb_mass_CSW* csw, int transfer_len) (*udi->protocol_m->reset)(udi); status = B_ERROR; break; - } + } trace_CSW(udi, csw); break; /* CSW was read successfully */ }while(try++ < 2); @@ -256,7 +256,7 @@ read_status(usb_device_info *udi, usb_mass_CSW* csw, int transfer_len) \fn:bulk_only_initialize \param udi: device on wich we should perform initialization \return:error code if initialization failed or B_OK if it passed - + initialize procedure for bulk only protocol devices. */ status_t @@ -270,7 +270,7 @@ bulk_only_initialize(usb_device_info *udi) \fn:bulk_only_reset \param udi: device on wich we should perform reset \return:error code if reset failed or B_OK if it passed - + reset procedure for bulk only protocol devices. Tries to send BulkOnlyReset USB request and clear USB_FEATURE_ENDPOINT_HALT features on input and output pipes. ([2] 3.1) @@ -295,13 +295,13 @@ bulk_only_reset(usb_device_info *udi) USB_FEATURE_ENDPOINT_HALT))) { PTRACE_ALWAYS(udi, "bulk_only_reset: clear_feature on pipe_out failed: %08x\n", status); - } + } PTRACE(udi, "bulk_only_reset:%08x\n", status); return status; } /** \fn:bulk_only_transfer - \param udi: corresponding device + \param udi: corresponding device \param cmd: SCSI command to be performed on USB device \param cmdlen: length of SCSI command \param data_sg: io vectors array with data to transfer @@ -311,7 +311,7 @@ bulk_only_reset(usb_device_info *udi) \param ccbio: CCB_SCSIIO struct for original SCSI command \param cb: callback to handle of final stage of command performing (autosense \ request etc.) - + transfer procedure for bulk-only protocol. Performs SCSI command on USB device [2] */ @@ -352,7 +352,7 @@ bulk_only_transfer(usb_device_info *udi, uint8 *cmd, uint8 cmdlen, //sg_buffer command_status = B_CMD_WIRE_FAILED; break; } - } + } /* get status of command */ status = read_status(udi, &csw, transfer_len); if(B_OK != status){ diff --git a/src/add-ons/kernel/busses/scsi/usb/proto_bulk.h b/src/add-ons/kernel/busses/scsi/usb/proto_bulk.h index 8ca165f186..632eace8c9 100644 --- a/src/add-ons/kernel/busses/scsi/usb/proto_bulk.h +++ b/src/add-ons/kernel/busses/scsi/usb/proto_bulk.h @@ -1,25 +1,25 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** bulk-only protocol "standard" procedures */ -#ifndef _PROTO_BULK_H_ +#ifndef _PROTO_BULK_H_ #define _PROTO_BULK_H_ -#ifndef _PROTO_MODULE_H_ +#ifndef _PROTO_MODULE_H_ #include "proto_module.h" -#endif /* _PROTO_MODULE_H_ */ +#endif /* _PROTO_MODULE_H_ */ extern protocol_module_info bulk_only_protocol_m; -#endif /*_PROTO_BULK_H_*/ +#endif /*_PROTO_BULK_H_*/ diff --git a/src/add-ons/kernel/busses/scsi/usb/proto_cbi.c b/src/add-ons/kernel/busses/scsi/usb/proto_cbi.c index 6973c972b0..f3a53e379a 100644 --- a/src/add-ons/kernel/busses/scsi/usb/proto_cbi.c +++ b/src/add-ons/kernel/busses/scsi/usb/proto_cbi.c @@ -1,14 +1,14 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /* References: * USB Mass Storage Class specifications: @@ -19,17 +19,17 @@ #include -#include "usb_scsi.h" +#include "usb_scsi.h" -#include "device_info.h" +#include "device_info.h" -#include "proto_module.h" +#include "proto_module.h" #include "proto_common.h" -#include "proto_cbi.h" +#include "proto_cbi.h" -#include "usb_defs.h" +#include "usb_defs.h" -#define USB_REQ_CBI_ADSC 0x00 +#define USB_REQ_CBI_ADSC 0x00 typedef struct _usb_mass_CBI_CB{ @@ -38,8 +38,8 @@ typedef struct _usb_mass_CBI_CB{ uint8 padding[14]; } usb_mass_CBI_CB; -#define CDB_LEN 16 -#define CDB_RESET_LEN 12 +#define CDB_LEN 16 +#define CDB_RESET_LEN 12 //typedef uint8 usb_mass_CDB[CDB_LEN]; @@ -81,7 +81,7 @@ static void cbi_transfer(usb_device_info *udi, uint8 *cmd, uint8 cmdlen, //sg_bu void trace_CDB(usb_device_info *udi, const usb_mass_CBI_CB *cb, int len) { PTRACE(udi, "CB:{op:0x%02x; op2:0x%02x;}\n", cb->op, cb->op2); - udi->trace_bytes(" padding:", cb->padding, len - 2); + udi->trace_bytes(" padding:", cb->padding, len - 2); } static status_t @@ -143,7 +143,7 @@ parse_status(usb_device_info *udi, usb_mass_CBI_IDB *idb) break; } } /* else ?? */ - } + } return command_status; } @@ -153,14 +153,14 @@ parse_status(usb_device_info *udi, usb_mass_CBI_IDB *idb) \fn: \param udi: ??? \return:?? - + ?? */ status_t cbi_reset(usb_device_info *udi) { status_t status = B_ERROR; - //usb_mass_CBI_CB *cb = CB_BUFFER(udi->proto_buf); + //usb_mass_CBI_CB *cb = CB_BUFFER(udi->proto_buf); //usb_mass_CDB cdb = {0x1d, 0x04, 0x00}; //memset(cdb + 2, 0xff, CDB_RESET_LEN - 2); usb_mass_CBI_CB cb = { @@ -171,7 +171,7 @@ cbi_reset(usb_device_info *udi) status = send_request_adsc(udi, &cb, CDB_RESET_LEN); if(status != B_OK) PTRACE_ALWAYS(udi, "command_block_reset: reset request failed: %08x\n", status); - + if(B_OK != (status = (*udi->usb_m->clear_feature)(udi->pipe_in, USB_FEATURE_ENDPOINT_HALT))) PTRACE_ALWAYS(udi, "command_block_reset: clear_feature on pipe_in failed: %08x\n", status); @@ -201,7 +201,7 @@ cbi_initialize(usb_device_info *udi) \param cmd: ??? \param cmdlen: ??? \return:??? - + ??? */ void @@ -225,7 +225,7 @@ cbi_transfer(usb_device_info *udi, uint8 *cmd, uint8 cmdlen, (*udi->protocol_m->reset)(udi); } break; - } + } if(transfer_len != 0){ status = process_data_io(udi, sg_data, sg_count, dir); if(status != B_OK){ @@ -233,8 +233,8 @@ cbi_transfer(usb_device_info *udi, uint8 *cmd, uint8 cmdlen, break; } } - - if(PROTO(udi->properties) == PROTO_CBI){ + + if(PROTO(udi->properties) == PROTO_CBI){ status = request_interrupt(udi, &idb); PTRACE(udi, "cbi_transfer:request interrupt: %08x(%08x)\n", status, udi->status); if(status != B_OK){ @@ -246,9 +246,9 @@ cbi_transfer(usb_device_info *udi, uint8 *cmd, uint8 cmdlen, command_status = parse_status(udi, &idb); } else { /* PROP_CB ???*/ command_status = B_CMD_UNKNOWN; - } + } residue = 0; /* DEBUG!!!!!!!!!*/ - }while(false); + }while(false); cb(udi, ccbio, residue, command_status); } diff --git a/src/add-ons/kernel/busses/scsi/usb/proto_cbi.h b/src/add-ons/kernel/busses/scsi/usb/proto_cbi.h index cbb002d7cf..9c994cd62b 100644 --- a/src/add-ons/kernel/busses/scsi/usb/proto_cbi.h +++ b/src/add-ons/kernel/busses/scsi/usb/proto_cbi.h @@ -1,22 +1,22 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ -#ifndef _PROTO_CBI_H_ +#ifndef _PROTO_CBI_H_ #define _PROTO_CBI_H_ -#ifndef _PROTO_MODULE_H_ +#ifndef _PROTO_MODULE_H_ #include "proto_module.h" -#endif /* _PROTO_MODULE_H_ */ - +#endif /* _PROTO_MODULE_H_ */ + extern protocol_module_info cbi_protocol_m; -#endif /*_PROTO_CBI_H_*/ +#endif /*_PROTO_CBI_H_*/ diff --git a/src/add-ons/kernel/busses/scsi/usb/proto_common.c b/src/add-ons/kernel/busses/scsi/usb/proto_common.c index c4bcd23698..593ac87f2a 100644 --- a/src/add-ons/kernel/busses/scsi/usb/proto_common.c +++ b/src/add-ons/kernel/busses/scsi/usb/proto_common.c @@ -1,24 +1,24 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ #include #include "usb_scsi.h" - -#include "device_info.h" -#include "proto_common.h" -#include "tracing.h" -#include "usb_defs.h" -#include "scsi_commands.h" + +#include "device_info.h" +#include "proto_common.h" +#include "tracing.h" +#include "usb_defs.h" +#include "scsi_commands.h" /** \fn:bulk_callback @@ -27,7 +27,7 @@ \param data:??? \param actual_len:??? \return:??? - + ??? */ void bulk_callback(void *cookie, status_t status, void* data, uint32 actual_len) @@ -40,14 +40,14 @@ void bulk_callback(void *cookie, status_t status, void* data, uint32 actual_len) udi->actual_len = actual_len; if(udi->status != B_CANCELED) release_sem(udi->trans_sem); - } + } } /** \fn:exec_io \param udi: ??? \return:??? - + ??? */ status_t process_data_io(usb_device_info *udi, //sg_buffer *sgb, @@ -64,15 +64,15 @@ status_t process_data_io(usb_device_info *udi, //sg_buffer *sgb, if(udi->status == B_DEV_STALLED){ status_t st=(*udi->usb_m->clear_feature)(pipe, USB_FEATURE_ENDPOINT_HALT); TRACE_ALWAYS("clear_on_STALL:%08x\n",st); - } + } }else{ - TRACE_ALWAYS("process_data_io:acquire_sem failed:%08x\n", status); + TRACE_ALWAYS("process_data_io:acquire_sem failed:%08x\n", status); (*udi->usb_m->cancel_queued_transfers)(pipe); - } + } } else { TRACE_ALWAYS("process_data_io:queue_bulk_v failed:%08x\n", status); } - TRACE_DATA_IO("process_data_io:processed:%d;status:%08x\n", udi->actual_len, status); + TRACE_DATA_IO("process_data_io:processed:%d;status:%08x\n", udi->actual_len, status); return status; } @@ -124,7 +124,7 @@ void sense_callback(struct _usb_device_info *udi, CCB_SCSIIO *ccbio, { ccbio->cam_sense_resid = residue; switch(status){ - case B_CMD_UNKNOWN: + case B_CMD_UNKNOWN: case B_CMD_FAILED: case B_OK:{ bool b_own_data = (ccbio->cam_sense_ptr == NULL); @@ -147,7 +147,7 @@ void sense_callback(struct _usb_device_info *udi, CCB_SCSIIO *ccbio, // ccbio->cam_ch.cam_status = CAM_REQ_CMP_ERR /*| CAM_AUTOSNS_VALID*/; // ccbio->cam_scsi_status = SCSI_STATUS_CHECK_CONDITION; TRACE("sense_callback: sense still not handled...\n"); - } + } } } break; diff --git a/src/add-ons/kernel/busses/scsi/usb/proto_common.h b/src/add-ons/kernel/busses/scsi/usb/proto_common.h index 74f74d60bc..a7af9438f0 100644 --- a/src/add-ons/kernel/busses/scsi/usb/proto_common.h +++ b/src/add-ons/kernel/busses/scsi/usb/proto_common.h @@ -1,16 +1,16 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ -#ifndef _PROTO_COMMON_H_ +#ifndef _PROTO_COMMON_H_ #define _PROTO_COMMON_H_ #ifndef _DEVICE_INFO_H_ @@ -18,9 +18,9 @@ #endif /* _DEVICE_INFO_H_ */ void bulk_callback(void *cookie, status_t status, void* data, uint32 actual_len); - + status_t process_data_io(usb_device_info *udi, iovec *sg_data, int32 sg_count/*sg_buffer *sgb*/, EDirection dir); - + void transfer_callback(usb_device_info *udi, CCB_SCSIIO *ccbio, int32 residue, status_t status); void sense_callback(usb_device_info *udi, CCB_SCSIIO *ccbio, diff --git a/src/add-ons/kernel/busses/scsi/usb/proto_module.h b/src/add-ons/kernel/busses/scsi/usb/proto_module.h index b97a67b9cd..690262229e 100644 --- a/src/add-ons/kernel/busses/scsi/usb/proto_module.h +++ b/src/add-ons/kernel/busses/scsi/usb/proto_module.h @@ -1,16 +1,16 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ -#ifndef _PROTO_MODULE_H_ +#ifndef _PROTO_MODULE_H_ #define _PROTO_MODULE_H_ #ifndef _MODULE_H @@ -22,7 +22,7 @@ #endif / *_SG_BUFFER_H_*/ enum { - /* B_OK */ /* JFYI:command is OK */ + /* B_OK */ /* JFYI:command is OK */ B_CMD_FAILED = B_ERRORS_END + 1, /* command failed */ B_CMD_WIRE_FAILED, /* device problems */ B_CMD_UNKNOWN, /* command state unknown */ @@ -43,9 +43,9 @@ typedef void (*ud_transfer_callback)(struct _usb_device_info *udi, typedef struct { module_info module; - - status_t (*init)(struct _usb_device_info *udi); - status_t (*reset)(struct _usb_device_info *udi); + + status_t (*init)(struct _usb_device_info *udi); + status_t (*reset)(struct _usb_device_info *udi); void (*transfer)(struct _usb_device_info *udi, uint8 *cmd, uint8 cmdlen, //sg_buffer *sgb, @@ -54,7 +54,7 @@ typedef struct { int32 transfer_len, EDirection dir, CCB_SCSIIO *ccbio, - ud_transfer_callback cb); + ud_transfer_callback cb); } protocol_module_info; @@ -63,10 +63,10 @@ typedef struct { status_t (*transform)(struct _usb_device_info *udi, uint8 *cmd, uint8 len, - uint8 **rcmd, uint8 *rlen); + uint8 **rcmd, uint8 *rlen); } transform_module_info; -#define MODULE_PREFIX "generic/usb_scsi_extensions/" +#define MODULE_PREFIX "generic/usb_scsi_extensions/" #define PROTOCOL_SUFFIX "/protocol/v1" #define TRANSFORM_SUFFIX "/transform/v1" #define PROTOCOL_MODULE_MASK MODULE_PREFIX"%s"PROTOCOL_SUFFIX @@ -74,13 +74,13 @@ typedef struct { /** \define:_TRACE_ALWAYS - trace always - used mainly for error messages + trace always - used mainly for error messages */ #define PTRACE_ALWAYS(__udi, __x...) \ { /*if(__udi->b_trace)*/ __udi->trace(true, __x); } /** \define:TRACE - trace only if logging is activated + trace only if logging is activated */ #define PTRACE(__udi, __x...) \ { if(__udi->b_trace) __udi->trace(false, __x); } diff --git a/src/add-ons/kernel/busses/scsi/usb/settings.c b/src/add-ons/kernel/busses/scsi/usb/settings.c index 9b154c3a4e..dd0c595de5 100644 --- a/src/add-ons/kernel/busses/scsi/usb/settings.c +++ b/src/add-ons/kernel/busses/scsi/usb/settings.c @@ -1,20 +1,20 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** driver settings support implementation */ #include "usb_scsi.h" #include "settings.h" -//#include "proto_common.h" +//#include "proto_common.h" #include /* strtoul */ #include /* strncpy */ @@ -37,46 +37,46 @@ bool b_ignore_sysinit2 = false; settings_keys array. */ enum SKKeys{ - skkVendor = 0, - skkDevice, -// skkName, -// skkTransport, - skkProtocol, - skkCommandSet, - skkFakeInq, - skk6ByteCmd, + skkVendor = 0, + skkDevice, +// skkName, +// skkTransport, + skkProtocol, + skkCommandSet, + skkFakeInq, + skk6ByteCmd, skkTransTU, skkNoTU, - skkNoGetMaxLUN, - skkNoPreventMedia, - skkUseModeSense10, - skkForceReadOnly, - skkProtoBulk, - skkProtoCB, + skkNoGetMaxLUN, + skkNoPreventMedia, + skkUseModeSense10, + skkForceReadOnly, + skkProtoBulk, + skkProtoCB, skkProtoCBI, // skkProtoFreecom, - skkCmdSetSCSI, - skkCmdSetUFI, - skkCmdSetATAPI, - skkCmdSetRBC, - skkCmdSetQIC157, - + skkCmdSetSCSI, + skkCmdSetUFI, + skkCmdSetATAPI, + skkCmdSetRBC, + skkCmdSetQIC157, + skkKeysCount, -// skkTransportBase = skkSubClassSCSI, - skkProtoBegin = skkProtoBulk, - skkProtoEnd = skkProtoCBI, - skkCmdSetBegin = skkCmdSetSCSI, - skkCmdSetEnd = skkCmdSetQIC157, +// skkTransportBase = skkSubClassSCSI, + skkProtoBegin = skkProtoBulk, + skkProtoEnd = skkProtoCBI, + skkCmdSetBegin = skkCmdSetSCSI, + skkCmdSetEnd = skkCmdSetQIC157, }; /** - helper struct, used in our "quick" search algorithm + helper struct, used in our "quick" search algorithm */ struct _settings_key{ union _hash{ char name[32]; uint16 key; }hash; - uint32 property; + uint32 property; }settings_keys[] = { /**< array of keys, used in our settings files */ {{"vendor" }, 0}, /* MUST BE SYNCHRONISED WITH skk*** indexes!!! */ {{"device" }, 0}, @@ -105,7 +105,7 @@ struct _settings_key{ /** \define:SK_EQUAL checks is the __name parameter correspond to value, pointed by __id index - in settings_keys array. The magic of our "quick" search algorithm =-)) + in settings_keys array. The magic of our "quick" search algorithm =-)) */ #define CAST_SK(__name) (*(uint16 *)(__name)) #define SK_EQUAL(__name, __id) ((CAST_SK(__name) == (settings_keys[__id].hash.key)) && \ @@ -114,7 +114,7 @@ struct _settings_key{ \fn:load_module_settings loads driver settings from extarnal settings file through BeOS driver settings API. Called on initialization of the module -*/ +*/ void load_module_settings(void) { void *sh = load_driver_settings(MODULE_NAME); @@ -128,25 +128,25 @@ void load_module_settings(void) b_ignore_sysinit2 = get_driver_boolean_parameter(sh, "ignore_sysinit2", b_ignore_sysinit2, false); if(reserved_devices > MAX_DEVICES_COUNT) - reserved_devices = MAX_DEVICES_COUNT; + reserved_devices = MAX_DEVICES_COUNT; if(reserved_luns > MAX_LUNS_COUNT) reserved_luns = MAX_LUNS_COUNT; b_reservation_on = (reserved_devices != 0); - + unload_driver_settings(sh); } else { TRACE("settings:load:file '%s' was not found. Using default setting...\n", MODULE_NAME); - } + } } /** \fn:strncpy_value \param to: buffer for copied string \param dp: driver_parameter, from wich copied string come - \param size: maximal size of copied string + \param size: maximal size of copied string copies a string, containing value[0] of this parameter, from driver_parameter, pointed by dp, to buffer pointed by to. Semantic of this function is similar - to standard strncpy() one. + to standard strncpy() one. */ /*static void strncpy_value(char *to, driver_parameter *dp, size_t size) @@ -162,7 +162,7 @@ strncpy_value(char *to, driver_parameter *dp, size_t size) \return: a bitmasked value from PROP_-defined flags for USB subclass and \ protocol parse the transport driver_parameter for known USB subclasses, protocols and - compose a bitmasked value from those settings + compose a bitmasked value from those settings */ static uint32 parse_transport(driver_parameter *dp, int skkBase, int skkEnd, @@ -185,14 +185,14 @@ parse_transport(driver_parameter *dp, int skkBase, int skkEnd, if(dp->value_count > 1){ TRACE("settings:parse_transport:accept '%s', ignore extra...\n", value); } - } + } return ret; } /** \fn:lookup_device_info \param product_id: product id of device to be checked for private settings \param dp: driver_parameter, containing device information - \param udd: on return contains name,protocol etc. information about device + \param udd: on return contains name,protocol etc. information about device \return: "true" if private settings for device found - "false" otherwise looks through device parameter, pointed by dp, obtains the name and other parameters of private device settings if available @@ -218,12 +218,12 @@ lookup_device_info(uint16 product_id, driver_parameter *dp, } else*/ if(SK_EQUAL(dp->parameters[prm].name, skkProtocol)){ uds->properties |= parse_transport(&dp->parameters[prm], - skkProtoBegin, skkProtoEnd, + skkProtoBegin, skkProtoEnd, PROTO_VENDOR, uds->vendor_protocol); } else if(SK_EQUAL(dp->parameters[prm].name, skkCommandSet)){ uds->properties |= parse_transport(&dp->parameters[prm], - skkCmdSetBegin, skkCmdSetEnd, + skkCmdSetBegin, skkCmdSetEnd, CMDSET_VENDOR, uds->vendor_commandset); } else if(SK_EQUAL(dp->parameters[prm].name, skkFakeInq)){ @@ -234,10 +234,10 @@ lookup_device_info(uint16 product_id, driver_parameter *dp, } else if(SK_EQUAL(dp->parameters[prm].name, skkTransTU)){ uds->properties |= FIX_TRANS_TEST_UNIT; - } else + } else if(SK_EQUAL(dp->parameters[prm].name, skkNoTU)){ uds->properties |= FIX_NO_TEST_UNIT; - } else + } else if(SK_EQUAL(dp->parameters[prm].name, skkNoPreventMedia)){ uds->properties |= FIX_NO_PREVENT_MEDIA; } else @@ -276,7 +276,7 @@ lookup_vendor_info(uint16 vendor_id, uint16 product_id, driver_parameter *dp, usb_device_settings *uds) { bool b_found = false; - if(dp && dp->value_count > 0 && dp->values[0]){ + if(dp && dp->value_count > 0 && dp->values[0]){ uint16 id = strtoul(dp->values[0], NULL, 0) & 0xffff; if(vendor_id == id){ int i = 0; @@ -302,7 +302,7 @@ lookup_vendor_info(uint16 vendor_id, uint16 product_id, \param udd: on return contains name,protocol etc. information about device \return: "true" if private settings for device found - "false" otherwise looks through driver settings file for private device description and load it - if available into struct pointed by udd + if available into struct pointed by udd */ bool lookup_device_settings(const usb_device_descriptor *udd, usb_device_settings *uds) @@ -322,10 +322,10 @@ bool lookup_device_settings(const usb_device_descriptor *udd, if(b_found){ uds->vendor_id = udd->vendor_id; break; //we've got it - stop enumeration. - } + } } } /*for(...) - enumerate "root" parameters*/ - } /* if(ds) */ + } /* if(ds) */ unload_driver_settings(sh); } /* if(sh) */ if(b_found){ diff --git a/src/add-ons/kernel/busses/scsi/usb/settings.h b/src/add-ons/kernel/busses/scsi/usb/settings.h index 68c8161bc1..18969c2e19 100644 --- a/src/add-ons/kernel/busses/scsi/usb/settings.h +++ b/src/add-ons/kernel/busses/scsi/usb/settings.h @@ -1,18 +1,18 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** driver settings support definitions */ -#ifndef _USB_SCSI_SETTINGS_H_ +#ifndef _USB_SCSI_SETTINGS_H_ #define _USB_SCSI_SETTINGS_H_ void load_module_settings(void); @@ -31,8 +31,8 @@ bool lookup_device_settings(const usb_device_descriptor *udd, extern int reserved_devices; extern int reserved_luns; -extern bool b_reservation_on; +extern bool b_reservation_on; extern bool b_ignore_sysinit2; -#endif /*_USB_SCSI_SETTINGS_H_*/ +#endif /*_USB_SCSI_SETTINGS_H_*/ diff --git a/src/add-ons/kernel/busses/scsi/usb/sg_buffer.c b/src/add-ons/kernel/busses/scsi/usb/sg_buffer.c index 1eafe16960..930b5a60cb 100644 --- a/src/add-ons/kernel/busses/scsi/usb/sg_buffer.c +++ b/src/add-ons/kernel/busses/scsi/usb/sg_buffer.c @@ -1,23 +1,23 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** handling SCSI data-buffer (both usual "plain" and scatter/gather ones) */ #include -#include "usb_scsi.h" +#include "usb_scsi.h" #include -#include "tracing.h" +#include "tracing.h" #include "sg_buffer.h" /** @@ -77,7 +77,7 @@ realloc_sg_buffer(sg_buffer *sgb, size_t size) status_t sg_access_byte(sg_buffer *sgb, off_t offset, uchar *byte, bool b_set) { - status_t status = B_ERROR; + status_t status = B_ERROR; int i = 0; for(; i < sgb->count; i++){ if(offset >= sgb->piov[i].iov_len){ @@ -101,7 +101,7 @@ sg_memcpy(sg_buffer *d_sgb, off_t d_offset, sg_buffer *s_sgb, off_t s_offset, size_t size) { status_t status = B_NO_INIT; - while(0 != d_sgb && 0 != s_sgb){ + while(0 != d_sgb && 0 != s_sgb){ uchar *d_ptr = 0; uchar *s_ptr = 0; status = B_ERROR; @@ -166,7 +166,7 @@ sg_buffer_len(sg_buffer *sgb, size_t *size) { status_t status = B_NO_INIT; if(0!=sgb && 0!=size){ - int i = 0; + int i = 0; *size = 0; for(; i < sgb->count; i++){ *size += sgb->piov[i].iov_len; diff --git a/src/add-ons/kernel/busses/scsi/usb/sg_buffer.h b/src/add-ons/kernel/busses/scsi/usb/sg_buffer.h index 736f74632e..f5e71b83c6 100644 --- a/src/add-ons/kernel/busses/scsi/usb/sg_buffer.h +++ b/src/add-ons/kernel/busses/scsi/usb/sg_buffer.h @@ -1,18 +1,18 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** handling SCSI data-buffer (both usual "plain" and scatter/gather ones) */ - -#ifndef _SG_BUFFER_H_ + +#ifndef _SG_BUFFER_H_ #define _SG_BUFFER_H_ #ifndef _IOVEC_H @@ -40,5 +40,5 @@ status_t sg_memcpy(sg_buffer *dest_sgb, off_t dest_offset, sg_buffer *src_sgb, off_t src_offset, size_t size); void free_sg_buffer(sg_buffer *sgb); -#endif /*_SG_BUFFER_H_*/ +#endif /*_SG_BUFFER_H_*/ diff --git a/src/add-ons/kernel/busses/scsi/usb/tracing.c b/src/add-ons/kernel/busses/scsi/usb/tracing.c index 9adbd7c423..d11855ab37 100644 --- a/src/add-ons/kernel/busses/scsi/usb/tracing.c +++ b/src/add-ons/kernel/busses/scsi/usb/tracing.c @@ -1,14 +1,14 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** tracing support implementation */ @@ -18,15 +18,15 @@ #include #include /* posix file i/o - create, write, close */ #include -#include -#include +#include +#include /** private log path name */ static const char *private_log_path = "/var/log/"MODULE_NAME".log"; static const char *log_port_name = MODULE_NAME"-logging"; -#ifdef BUILD_LOG_DAEMON +#ifdef BUILD_LOG_DAEMON int main(int argc, char**argv) { @@ -45,10 +45,10 @@ int main(int argc, char**argv) FILE *f = fopen(private_log_path, "a"); fwrite(buffer, sz, 1, f); fclose(f); - } + } } } - } + } return 0; } @@ -56,7 +56,7 @@ int main(int argc, char**argv) /** is activity logging on or off? */ #if DEBUG -bool b_log = true; +bool b_log = true; #else bool b_log = false; #endif @@ -79,7 +79,7 @@ static bool b_log_time = false; /** log thread id from wich logging performed */ static bool b_log_thid = false; /** log thread name from wich logging performed */ -static bool b_log_thname = false; +static bool b_log_thname = false; /** semaphore id used to synchronizing logging requests */ //static sem_id loglock; /** log result of READ_CAPACITY command */ @@ -118,11 +118,11 @@ load_log_settings(void *sh) b_log_data_processing = get_driver_boolean_parameter(sh, "debug_trace_data_io", b_log_data_processing, false); - b_log_sense_data = + b_log_sense_data = get_driver_boolean_parameter(sh, "debug_trace_sense_data", b_log_sense_data, false); b_log_capacity = get_driver_boolean_parameter(sh, "debug_trace_capacity", - b_log_capacity, false); + b_log_capacity, false); if(!b_log_file){ /* some information is already in system log entries */ b_log_thid = false; b_log_thname = false; @@ -144,7 +144,7 @@ create_log(void) /** \fn: usb_scsi_trace - \param b_force: if true - output message ignoring current logging state + \param b_force: if true - output message ignoring current logging state \param fmt: format string used in message formatting \param ...: variable argument used in message formatting formats and traces messages to current debug output target. @@ -267,13 +267,13 @@ usb_scsi_trace_CCB_SCSIIO(const CCB_SCSIIO *ccbio) ccbio->cam_vu_flags, ccbio->cam_tag_action); - usb_scsi_trace_bytes("CDB_UN:\n", ccbio->cam_cdb_io.cam_cdb_bytes, IOCDBLEN); + usb_scsi_trace_bytes("CDB_UN:\n", ccbio->cam_cdb_io.cam_cdb_bytes, IOCDBLEN); } /** \fn: usb_scsi_command_trace \param b_hlight: highlight command and prefix it with spec. charachter \param cmd: array of bytes to be traced. typically pointer SCSI command buffer - \param cmdlen: size of buffer in cmd parameter + \param cmdlen: size of buffer in cmd parameter traces SCSI commands into debug output target.can highlight and prefix the text with special charachter and color for two different types of commands. @@ -294,7 +294,7 @@ usb_scsi_trace_command(bool b_hlight, const uint8 *cmd, size_t cmdlen) /** \fn:usb_scsi_bytes_trace \param bytes:array of bytes to be traced. - \param bytes_len: size of buffer in bytes parameter + \param bytes_len: size of buffer in bytes parameter traces buffer bytes one by one into debug output target. */ void @@ -319,7 +319,7 @@ usb_scsi_trace_bytes(const char *prefix, const uint8 *bytes, size_t bytes_len) } else { TRACE_ALWAYS("usb_scsi_trace_bytes:error allocate " "memory for tracing %d bytes\n", len); - } + } } void usb_scsi_trace_sgb(const char *prefix, sg_buffer *sgb) @@ -360,8 +360,8 @@ void usb_scsi_trace_SG(iovec *sg, int count) char sg_mask[] = "SG:{%s}\n"; char truncTail[] = ""; size_t trunc_count = min(count, 0x20); /* length watchdog */ - size_t len = sizeof(sg_mask) + sizeof(truncTail) + trunc_count * 16; - char *pbuf = (char *)malloc(len + 1); + size_t len = sizeof(sg_mask) + sizeof(truncTail) + trunc_count * 16; + char *pbuf = (char *)malloc(len + 1); if(pbuf){ int i = 0; char *p = pbuf; @@ -372,13 +372,13 @@ void usb_scsi_trace_SG(iovec *sg, int count) /* user should be informed about truncation too*/ if(trunc_count < count) strcpy(p, truncTail); - + TRACE(sg_mask, pbuf); free(pbuf); } else { TRACE_ALWAYS("usb_scsi_trace_SG:error allocate " "memory for tracing %d SG entries\n", trunc_count); - } + } } #endif /* BUILD_LOG_DAEMON */ diff --git a/src/add-ons/kernel/busses/scsi/usb/tracing.h b/src/add-ons/kernel/busses/scsi/usb/tracing.h index 9b60f35ed1..455eef450d 100644 --- a/src/add-ons/kernel/busses/scsi/usb/tracing.h +++ b/src/add-ons/kernel/busses/scsi/usb/tracing.h @@ -1,24 +1,24 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** tracing support definitions */ -#ifndef _USB_SCSI_TRACING_H_ +#ifndef _USB_SCSI_TRACING_H_ #define _USB_SCSI_TRACING_H_ #ifndef _SG_BUFFER_H_ #include "sg_buffer.h" #endif /*_SG_BUFFER_H_*/ - + void load_log_settings(void *sh); void create_log(void); void usb_scsi_trace(bool b_force, const char *fmt, ...); @@ -32,13 +32,13 @@ void usb_scsi_trace_CCB_SCSIIO(const CCB_SCSIIO *ccbio); /* ---------------------- Generic tracing --------------------------------------- */ /** \define:TRACE_ALWAYS - trace always - used mainly for error messages + trace always - used mainly for error messages */ #define TRACE_ALWAYS(x...) \ usb_scsi_trace(true, x) /** \define:TRACE - trace only if logging is activated + trace only if logging is activated */ #define TRACE(x...) \ usb_scsi_trace(false, x) @@ -48,7 +48,7 @@ extern bool b_log_scsi_cmd; void usb_scsi_trace_command(bool b_hlight, const uint8 *cmd, size_t cmdlen); /** \define:TRACE_SCSI_COMMAND - trace SCSI command + trace SCSI command */ #define TRACE_SCSI_COMMAND(cmd, cmdlen)\ { if(b_log_scsi_cmd) usb_scsi_trace_command(false, cmd, cmdlen); } @@ -89,7 +89,7 @@ extern bool b_log_sense_data; trace the information REQUEST SENSE data. */ #define TRACE_SENSE_DATA(data, len)\ - { if(b_log_sense_data) usb_scsi_trace_bytes("SENSE:", data, len); } + { if(b_log_sense_data) usb_scsi_trace_bytes("SENSE:", data, len); } #define TRACE_MODE_SENSE_DATA(prefix, data, len)\ { if(b_log_sense_data) usb_scsi_trace_bytes(prefix, data, len); } #define TRACE_MODE_SENSE_SGB(prefix, data)\ @@ -99,5 +99,5 @@ extern bool b_log_capacity; #define TRACE_CAPACITY(prefix, data)\ { if(b_log_capacity) usb_scsi_trace_sgb(prefix, data); } -#endif /*_USB_SCSI_TRACING_H_*/ +#endif /*_USB_SCSI_TRACING_H_*/ diff --git a/src/add-ons/kernel/busses/scsi/usb/transform_procs.h b/src/add-ons/kernel/busses/scsi/usb/transform_procs.h index fb19eca327..b31ad1cb77 100644 --- a/src/add-ons/kernel/busses/scsi/usb/transform_procs.h +++ b/src/add-ons/kernel/busses/scsi/usb/transform_procs.h @@ -1,23 +1,23 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** decalration of SCSI commands transformation procedures */ -#ifndef _TRANSFORM_PROCS_H_ +#ifndef _TRANSFORM_PROCS_H_ #define _TRANSFORM_PROCS_H_ -#ifndef _PROTO_MODULE_H_ +#ifndef _PROTO_MODULE_H_ #include "proto_module.h" -#endif /* _PROTO_MODULE_H_ */ +#endif /* _PROTO_MODULE_H_ */ /* transforms SCSI commands */ extern transform_module_info scsi_transform_m; /* transforms RBC commands */ @@ -28,4 +28,4 @@ extern transform_module_info ufi_transform_m; extern transform_module_info atapi_transform_m; /* transforms QIC-157 commands */ extern transform_module_info qic157_transform_m; -#endif /*_TRANSFORM_PROCS_H_*/ +#endif /*_TRANSFORM_PROCS_H_*/ diff --git a/src/add-ons/kernel/busses/scsi/usb/usb_defs.h b/src/add-ons/kernel/busses/scsi/usb/usb_defs.h index aedadedccb..d8a3fd17b4 100644 --- a/src/add-ons/kernel/busses/scsi/usb/usb_defs.h +++ b/src/add-ons/kernel/busses/scsi/usb/usb_defs.h @@ -1,26 +1,26 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** definitions that should be in system headers but ... */ -#ifndef _USB_DEFS_H_ +#ifndef _USB_DEFS_H_ #define _USB_DEFS_H_ // TODO: Shouldn't it be declared in system USB headers? #define USB_EP_ATTR_CONTROL 0x00 #define USB_EP_ATTR_ISOCHRONOUS 0x01 -#define USB_EP_ATTR_BULK 0x02 -#define USB_EP_ATTR_INTERRUPT 0x03 -#define USB_EP_ATTR_MASK 0x03 +#define USB_EP_ATTR_BULK 0x02 +#define USB_EP_ATTR_INTERRUPT 0x03 +#define USB_EP_ATTR_MASK 0x03 #define USB_EP_ADDR_DIR_IN 0x80 #define USB_EP_ADDR_DIR_OUT 0x00 @@ -42,5 +42,5 @@ //TODO: And this was in old v3 stack what now ??? #define B_DEV_STALLED 0x8000a015 /* some "forgotten" error */ -#endif /*_USB_DEFS_H_*/ +#endif /*_USB_DEFS_H_*/ diff --git a/src/add-ons/kernel/busses/scsi/usb/usb_scsi.c b/src/add-ons/kernel/busses/scsi/usb/usb_scsi.c index 3629d750cf..2a6320accf 100644 --- a/src/add-ons/kernel/busses/scsi/usb/usb_scsi.c +++ b/src/add-ons/kernel/busses/scsi/usb/usb_scsi.c @@ -1,18 +1,18 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ /** Main part of USB SIM implementation */ -#include "usb_scsi.h" +#include "usb_scsi.h" #include #include @@ -21,22 +21,22 @@ #include #include #include -#include "device_info.h" -#include "settings.h" -#include "transform_procs.h" -#include "tracing.h" -#include "scsi_commands.h" +#include "device_info.h" +#include "settings.h" +#include "transform_procs.h" +#include "tracing.h" +#include "scsi_commands.h" #include "proto_common.h" -#include "proto_bulk.h" -#include "proto_cbi.h" -#include "usb_defs.h" -#include "fake_device.h" -#include "sg_buffer.h" +#include "proto_bulk.h" +#include "proto_cbi.h" +#include "usb_defs.h" +#include "fake_device.h" +#include "sg_buffer.h" #if 0 status_t device_added(const usb_device device, void **cookie); - + status_t device_removed(void *cookie); static long sim_action(CCB_HEADER *ccbh); @@ -55,11 +55,11 @@ static long sim_init(); static long path_id = -1; static int32 load_count = 0; - + static char sim_vendor_name[] = "Haiku"; /* who wrote this driver */ static char hba_vendor_name[] = "USB"; /* who made the hardware */ static char controller_family[] = "USB SCSI"; /* what family of products */ - + struct usb_support_descriptor supported_devices[] = { {0, 0, 0, 0, 0} }; @@ -69,7 +69,7 @@ struct usb_support_descriptor supported_devices[] = { usb_device_info *usb_devices[MAX_DEVICES_COUNT]; /* main devices table locking semaphore */ sem_id usb_serial_lock = -1; - + usb_module_info *usb; static cam_for_sim_module_info *cam; @@ -95,7 +95,7 @@ static status_t xpt_extended_path_inquiry(CCB_EXTENDED_PATHINQ *ccbep); \param uii:??? \param pproperties:??? \return:B_BAD_TYPE , B_ENTRY_NOT_FOUND, B_OK - + ?? */ status_t get_interface_properties(usb_interface_info *uii, uint32 *pproperties) @@ -105,12 +105,12 @@ status_t get_interface_properties(usb_interface_info *uii, uint32 *pproperties) status = B_OK; switch(uii->descr->interface_subclass){ case USB_DEV_SUBCLASS_RBC: *pproperties |= CMDSET_RBC; break; - case USB_DEV_SUBCLASS_UFI: *pproperties |= CMDSET_UFI; break; - case USB_DEV_SUBCLASS_SFF8020I: + case USB_DEV_SUBCLASS_UFI: *pproperties |= CMDSET_UFI; break; + case USB_DEV_SUBCLASS_SFF8020I: case USB_DEV_SUBCLASS_SFF8070I: *pproperties |= CMDSET_ATAPI; break; case USB_DEV_SUBCLASS_SCSI: *pproperties |= CMDSET_SCSI; break; case USB_DEV_SUBCLASS_QIC157: *pproperties |= CMDSET_QIC157; break; - default: + default: TRACE_ALWAYS("get_interface_properties:unknown USB subclass:%02x\n", uii->descr->interface_subclass); /*status = B_ENTRY_NOT_FOUND;*/ /*B_BAD_TYPE assumed*/ @@ -120,7 +120,7 @@ status_t get_interface_properties(usb_interface_info *uii, uint32 *pproperties) case USB_DEV_PROTOCOL_CBI: *pproperties |= PROTO_CBI; break; case USB_DEV_PROTOCOL_CB: *pproperties |= PROTO_CB; break; case USB_DEV_PROTOCOL_BULK: *pproperties |= PROTO_BULK_ONLY; break; - default: + default: TRACE_ALWAYS("get_interface_properties:unknown USB protocol:%02x\n", uii->descr->interface_protocol); /*status = B_ENTRY_NOT_FOUND;*/ /*B_BAD_TYPE assumed*/ @@ -134,7 +134,7 @@ status_t get_interface_properties(usb_interface_info *uii, uint32 *pproperties) } /** \fn: - + */ status_t load_vendor_module(char **path, const char *path_mask, const char *prop, module_info **mi) @@ -154,7 +154,7 @@ status_t load_vendor_module(char **path, const char *path_mask, } /** \fn: - + */ status_t setup_transport_modules(usb_device_info *udi, usb_device_settings *uds) @@ -286,7 +286,7 @@ status_t setup_endpoints(usb_interface_info *uii, usb_device_info *udi) \param device:??? \param ppudi:??? \return:??? - + ??? */ status_t allocate_resources(usb_device_info *udi) @@ -310,11 +310,11 @@ status_t allocate_resources(usb_device_info *udi) udi->dev_num = dev; release_sem(udi->lock_sem); status = B_OK; - }else + }else status = udi->trans_sem; - } else + } else status = udi->lock_sem; - + if(status != B_OK){ TRACE_ALWAYS("allocate_resources:error:%s", strerror(status)); if(udi->lock_sem >= 0) @@ -333,7 +333,7 @@ status_t allocate_resources(usb_device_info *udi) } /** \fn: - + */ void release_resources(usb_device_info *udi) { @@ -352,7 +352,7 @@ void release_resources(usb_device_info *udi) \param device:?? \param cookie:?? \return:?? - + ?? */ status_t device_added(const usb_device device, void **cookie){ @@ -364,10 +364,10 @@ status_t device_added(const usb_device device, void **cookie){ const usb_device_descriptor *udd = (*usb->get_device_descriptor)(device); usb_device_info *udi = (usb_device_info *)malloc(sizeof(usb_device_info)); TRACE("device_added: probing canidate: " - "%04x/%04x %02d/%02d/%02d\n", + "%04x/%04x %02d/%02d/%02d\n", udd->vendor_id, udd->product_id, - udd->device_class, - udd->device_subclass, + udd->device_class, + udd->device_subclass, udd->device_protocol); if(udi){ status = B_NO_INIT; @@ -405,7 +405,7 @@ status_t device_added(const usb_device device, void **cookie){ if( B_OK == setup_transport_modules(udi, &ud_settings)){ break; } /* else - no break - fall through */ - default: + default: continue; /* skip to next interface */ } if(alt != 0){ /*TODO: are we need this ???*/ @@ -413,7 +413,7 @@ status_t device_added(const usb_device device, void **cookie){ TRACE_ALWAYS("device_added:setting alt interface failed:%s", strerror(status)); goto Failed;/* Break - is it right?*/ - } + } } if((*usb->get_configuration)(device) != uci){ if((status = (*usb->set_configuration)(device, uci)) != B_OK){ @@ -421,7 +421,7 @@ status_t device_added(const usb_device device, void **cookie){ (*usb->get_configuration)(device), uci); TRACE_ALWAYS("device_added:setting configuration failed:%s\n", strerror(status)); - + goto Failed;/* Break - is it right?*/ } } @@ -432,7 +432,7 @@ status_t device_added(const usb_device device, void **cookie){ udi->b_trace = b_log_protocol; udi->trace = usb_scsi_trace; udi->trace_bytes = usb_scsi_trace_bytes; - udi->trans_timeout = TRANS_TIMEOUT; + udi->trans_timeout = TRANS_TIMEOUT; udi->usb_m = usb; udi->not_ready_luns = 0xff; /*assume all LUNs initially not ready */ if((status = (*udi->protocol_m->init)(udi)) == B_OK){ @@ -440,7 +440,7 @@ status_t device_added(const usb_device device, void **cookie){ *cookie = udi; b_found = true; /* we have found something useful - time to go out! */ break; /* ... now break alternatives iteration.*/ - } else { + } else { release_resources(udi); } } @@ -457,26 +457,26 @@ status_t device_added(const usb_device device, void **cookie){ if(status != B_OK){ TRACE("device_added: probing failed (%s) for: %04x/%04x\n", strerror(status), udd->vendor_id, udd->product_id); - } -Failed: + } +Failed: return status; } /** \fn:device_removed \param cookie:??? \return:??? - + ??? */ status_t device_removed(void *cookie) { status_t status = B_OK; usb_device_info *udi = (usb_device_info *)cookie; - acquire_sem(udi->lock_sem); /* wait for possible I/O operation complete */ + acquire_sem(udi->lock_sem); /* wait for possible I/O operation complete */ release_resources(udi); /* no corresponding call of release_sem(udi->lock_sem); - semaphore was deleted in release_resources, any waiting thread - was failed with BAD_SEM_ID. + was failed with BAD_SEM_ID. */ TRACE_ALWAYS("device_removed[%d]:All The Best !!!\n", udi->dev_num); free(udi); @@ -486,7 +486,7 @@ status_t device_removed(void *cookie) /** \fn:sim_init \return: ??? - + called on SIM init */ static long sim_init(void) @@ -506,7 +506,7 @@ pre_check_scsi_io_request(usb_device_info *udi, CCB_SCSIIO *ccbio, uint8 target_lun = ccbio->cam_ch.cam_target_lun; *ret_status = B_OK; /* handle reserved device and luns entries */ - if(b_reservation_on && udi == NULL && + if(b_reservation_on && udi == NULL && target_id < reserved_devices && target_lun < reserved_luns) { @@ -535,7 +535,7 @@ pre_check_scsi_io_request(usb_device_info *udi, CCB_SCSIIO *ccbio, memset(&udi->autosense_data, 0, sizeof(udi->autosense_data)); } else { memset(ccbio->cam_sense_ptr, 0, ccbio->cam_sense_len); - } + } return true; } /** @@ -547,7 +547,7 @@ pre_handle_features(usb_device_info *udi, CCB_SCSIIO *ccbio, { uint8 target_lun = ccbio->cam_ch.cam_target_lun; *ret_status = B_OK; - udi->trans_timeout = TRANS_TIMEOUT; + udi->trans_timeout = TRANS_TIMEOUT; switch(command->opcode){ case MODE_SELECT_6: case MODE_SENSE_6:{ @@ -572,18 +572,18 @@ pre_handle_features(usb_device_info *udi, CCB_SCSIIO *ccbio, } TRACE_MODE_SENSE_SGB("MODE SELECT 6:", &sgb_sense_6); if(B_OK != sg_memcpy(sgb, 1, &sgb_sense_6, 0, 3) || - B_OK != sg_memcpy(sgb, 7, &sgb_sense_6, 3, 1) || + B_OK != sg_memcpy(sgb, 7, &sgb_sense_6, 3, 1) || B_OK != sg_memcpy(sgb, 8, &sgb_sense_6, 4, ccbio->cam_dxfer_len - sizeof(scsi_mode_param_header_6))) { /* In case of error TRACE-ing was already performed in sg_ functions */ goto set_REQ_INVALID_and_return; } TRACE_MODE_SENSE_SGB("MODE SELECT 10:", sgb); - } + } } /*else { if(b_select){ / * trace data if configured in settings * / TRACE_MODE_SENSE_DATA("MODE_SELECT:", ccbio->cam_data_ptr, ccbio->cam_dxfer_len); - } + } }*/ }break; case INQUIRY: /* fake INQUIRY request */ @@ -605,7 +605,7 @@ pre_handle_features(usb_device_info *udi, CCB_SCSIIO *ccbio, default: break; } return true; - + set_REQ_CMP_and_return: ccbio->cam_ch.cam_status = CAM_REQ_CMP; return false;//*ret_status = B_OK; @@ -625,11 +625,11 @@ post_handle_features(usb_device_info *udi, CCB_SCSIIO *ccbio, bool b_cmd_ok = (ccbio->cam_ch.cam_status == CAM_REQ_CMP); uint8 target_lun = ccbio->cam_ch.cam_target_lun; switch(command->opcode){ - case READ_6: + case READ_6: case WRITE_6: -#if 0 +#if 0 /* Disabled - single problem can switch to 6-bytes mode. If device doesn't - support 6-bytes command all goes totally wrong. That's bad. */ + support 6-bytes command all goes totally wrong. That's bad. */ if(!b_cmd_ok && !HAS_FEATURES(udi->descr.properties, PROP_FORCE_RW_TO_6)){ TRACE("post_handle_features:READ(10)/WRITE(10) failed - retry 6-byte one\n"); udi->descr.properties |= PROP_FORCE_RW_TO_6; @@ -668,13 +668,13 @@ post_handle_features(usb_device_info *udi, CCB_SCSIIO *ccbio, } TRACE_MODE_SENSE_SGB("MODE SENSE 10:", sgb); if( B_OK != sg_memcpy(&sgb_sense_6, 0, sgb, 1, 3) || - B_OK != sg_memcpy(&sgb_sense_6, 3, sgb, 7, 1) || + B_OK != sg_memcpy(&sgb_sense_6, 3, sgb, 7, 1) || B_OK != sg_memcpy(&sgb_sense_6, 4, sgb, 8, ccbio->cam_dxfer_len - sizeof(scsi_mode_param_header_6))) { /* In case of error TRACE-ing was already performed in sg_ functions */ TRACE_ALWAYS("MODE_SENSE 10->6 conversion failed\n"); goto set_REQ_INVALID_and_return; - } + } } /* set write-protected flag if required by user */ if(HAS_FIXES(udi->properties, FIX_FORCE_READ_ONLY)){ @@ -719,14 +719,14 @@ post_handle_features(usb_device_info *udi, CCB_SCSIIO *ccbio, set_REQ_INVALID_and_return: ccbio->cam_ch.cam_status = CAM_REQ_INVALID; *ret_status = B_BAD_VALUE; - return false; /* do not retry - fatal error */ + return false; /* do not retry - fatal error */ } /** \fn:xpt_scsi_io \param ccbio: ???? \return: ??? - - xpt_scsi_io - handle XPT_SCSI_IO sim action + + xpt_scsi_io - handle XPT_SCSI_IO sim action */ status_t xpt_scsi_io(CCB_SCSIIO *ccbio) { @@ -743,12 +743,12 @@ status_t xpt_scsi_io(CCB_SCSIIO *ccbio) } #if 0 /* activate if you need detailed logging of CCB_SCSI request*/ - usb_scsi_trace_CCB_SCSIIO(ccbio); + usb_scsi_trace_CCB_SCSIIO(ccbio); #endif /* acquire semaphore - avoid re-enters */ -/* if((status = acquire_sem_etc(udi->lock_sem, 1, +/* if((status = acquire_sem_etc(udi->lock_sem, 1, B_RELATIVE_TIMEOUT, udi->trans_timeout)) != B_OK) */ // TRACE_ALWAYS("sem before acq:%08x\n",udi->lock_sem); @@ -756,14 +756,14 @@ status_t xpt_scsi_io(CCB_SCSIIO *ccbio) /* disabled - CAM_BUSY flag is not recognized by BeOS ... :-( if(status == B_WOULD_BLOCK){ TRACE("locked sema bypass OK\n"); - ccbio->cam_ch.cam_status = CAM_BUSY; + ccbio->cam_ch.cam_status = CAM_BUSY; return B_OK; - }*/ + }*/ TRACE("xpt_scsi_io:acquire_sem_etc() failed:%08x\n", status); ccbio->cam_ch.cam_status = CAM_DEV_NOT_THERE; return B_DEV_BAD_DRIVE_NUM; } - /* set the command data pointer */ + /* set the command data pointer */ if(ccbio->cam_ch.cam_flags & CAM_CDB_POINTER){ cmd = ccbio->cam_cdb_io.cam_cdb_ptr; }else{ @@ -773,7 +773,7 @@ status_t xpt_scsi_io(CCB_SCSIIO *ccbio) *_handle_features() functions! Twice reallocation is also not awaited! Note this on refactoring!!! */ /*TODO returns!*/ - init_sg_buffer(&sgb, ccbio); + init_sg_buffer(&sgb, ccbio); do{ /* <-- will be repeated if 6-byte RW/MS commands failed */ uint8 *rcmd; uint8 rcmdlen; @@ -801,11 +801,11 @@ status_t xpt_scsi_io(CCB_SCSIIO *ccbio) case CAM_DIR_OUT: dir = eDirOut; break; default: dir = eDirNone; break; } - + TRACE_DATA_IO_SG(sgb.piov, sgb.count); - + /*TODO: return!*/ - sg_buffer_len(&sgb, &transfer_len); + sg_buffer_len(&sgb, &transfer_len); /* transfer command to device. SCSI status will be handled in callback */ (*udi->protocol_m->transfer)(udi, rcmd, rcmdlen, sgb.piov, sgb.count, transfer_len/*ccbio->cam_dxfer_len*/, @@ -820,26 +820,26 @@ status_t xpt_scsi_io(CCB_SCSIIO *ccbio) \fn:xpt_path_inquiry \param ccbp: \return: - - xpt_path_inquiry - handle XPT_PATH_INQ sim action + + xpt_path_inquiry - handle XPT_PATH_INQ sim action */ status_t xpt_path_inquiry(CCB_PATHINQ *ccbp) { status_t status = B_OK; - + ccbp->cam_version_num = SIM_VERSION; ccbp->cam_target_sprt = 0; ccbp->cam_hba_eng_cnt = 0; memset (ccbp->cam_vuhba_flags, 0, VUHBA); ccbp->cam_sim_priv = SIM_PRIV; ccbp->cam_async_flags = 0; - ccbp->cam_initiator_id = CONTROLLER_SCSI_ID; + ccbp->cam_initiator_id = CONTROLLER_SCSI_ID; ccbp->cam_hba_inquiry = CONTROLLER_SCSI_BUS; /* Narrow SCSI bus */ ccbp->cam_hba_misc = PIM_NOINQUIRY; ccbp->cam_osd_usage = 0; /* There should be special handling of path_id == 0xff but looks like it's not used by BeOS now */ - /*ccbp->cam_hpath_id = path_id;*/ + /*ccbp->cam_hpath_id = path_id;*/ strncpy(ccbp->cam_sim_vid, sim_vendor_name, SIM_ID); strncpy(ccbp->cam_hba_vid, hba_vendor_name, HBA_ID); ccbp->cam_ch.cam_status = CAM_REQ_CMP; @@ -849,13 +849,13 @@ status_t xpt_path_inquiry(CCB_PATHINQ *ccbp) \fn:xpt_extended_path_inquiry \param ccbep: ??? \return:??? - - xpt_extended_path_inquiry - handle XPT_EXTENDED_PATH_INQ sim action + + xpt_extended_path_inquiry - handle XPT_EXTENDED_PATH_INQ sim action */ status_t xpt_extended_path_inquiry(CCB_EXTENDED_PATHINQ *ccbep) { status_t status = B_OK; - xpt_path_inquiry((CCB_PATHINQ *)ccbep); + xpt_path_inquiry((CCB_PATHINQ *)ccbep); sprintf(ccbep->cam_sim_version, "%d.0", SIM_VERSION); sprintf(ccbep->cam_hba_version, "%d.0", HBA_VERSION); strncpy(ccbep->cam_controller_family, controller_family, FAM_ID); @@ -866,7 +866,7 @@ status_t xpt_extended_path_inquiry(CCB_EXTENDED_PATHINQ *ccbep) \fn:sim_action \param ccbh: ???? \return: ???? - + This fucntion performs SCSI interface module actions - calls corresponding xpt_* - functions. */ @@ -904,9 +904,9 @@ static long sim_action(CCB_HEADER *ccbh) \param op: operation to be performed on this module \param ...: possible additional arguments \return: B_OK on success, error status on failure - + This function deals with standard module operations. Currently, the only - two things that entails are initialization and uninitialization. + two things that entails are initialization and uninitialization. - get the SCSI Bus Manager Module and USB Manager Module - put them when we're finished */ @@ -920,15 +920,15 @@ static status_t std_ops(int32 op, ...) TRACE_ALWAYS("std_ops: B_MODULE_INIT called!\n"); /* if(0 == atomic_add(&load_count, 1)){ thread_info tinfo = {0}; */ - load_module_settings(); + load_module_settings(); /* get_thread_info(find_thread(0), &tinfo); if(!b_ignore_sysinit2 || (0 != strcmp(tinfo.name, "sysinit2"))){ - create_log(); - if(get_module(B_USB_MODULE_NAME, (module_info **)&usb) == B_OK){ - if(get_module(B_CAM_FOR_SIM_MODULE_NAME, (module_info **)&cam) == B_OK){ + create_log(); + if(get_module(B_USB_MODULE_NAME, (module_info **)&usb) == B_OK){ + if(get_module(B_CAM_FOR_SIM_MODULE_NAME, (module_info **)&cam) == B_OK){ for(i = 0; i < MAX_DEVICES_COUNT; i++) - usb_devices[i] = NULL; - + usb_devices[i] = NULL; + if((*usb->register_driver)(MODULE_NAME, supported_devices, SIZEOF(supported_devices), "usb_dsk") == B_OK){ if((*usb->install_notify)(MODULE_NAME, ¬ify_hooks) == B_OK){ entry.sim_init = sim_init; @@ -936,9 +936,9 @@ static status_t std_ops(int32 op, ...) path_id =(*cam->xpt_bus_register)(&entry); usb_serial_lock = create_sem(1, MODULE_NAME"_devices_table_lock"); status = B_OK; - break; - } - } + break; + } + } put_module(B_CAM_FOR_SIM_MODULE_NAME); } put_module(B_USB_MODULE_NAME); @@ -948,7 +948,7 @@ static status_t std_ops(int32 op, ...) } } else { atomic_add(&load_count, -1); - }*/ + }*/ break; case B_MODULE_UNINIT: TRACE_ALWAYS("std_ops: B_MODULE_UNINIT called!\n"); @@ -961,7 +961,7 @@ static status_t std_ops(int32 op, ...) } delete_sem(usb_serial_lock); put_module(B_USB_MODULE_NAME); - put_module(B_CAM_FOR_SIM_MODULE_NAME); + put_module(B_CAM_FOR_SIM_MODULE_NAME); } else { atomic_add(&load_count, 1); }*/ @@ -971,12 +971,12 @@ static status_t std_ops(int32 op, ...) } /** - * \fn: + * \fn: * \param : * \return: * TODO */ -static float +static float supports_device(device_node_handle parent, bool *_noConnection) { TRACE_ALWAYS("supports_device\n"); @@ -984,7 +984,7 @@ supports_device(device_node_handle parent, bool *_noConnection) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -997,7 +997,7 @@ register_device(device_node_handle parent) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1010,7 +1010,7 @@ init_module(device_node_handle node, void *user_cookie, void **_cookie) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1023,7 +1023,7 @@ uninit_module(void *cookie) } /** - * \fn: + * \fn: * \param : * TODO */ @@ -1034,7 +1034,7 @@ device_removed(device_node_handle node, void *cookie) } /** - * \fn: + * \fn: * \param : * TODO */ @@ -1045,7 +1045,7 @@ device_cleanup(device_node_handle node) } /** - * \fn: + * \fn: * \param : * TODO */ @@ -1056,7 +1056,7 @@ get_supported_paths(const char ***_busses, const char ***_devices) } /** - * \fn: + * \fn: * \param : * TODO */ @@ -1067,7 +1067,7 @@ scsi_io( scsi_sim_cookie cookie, scsi_ccb *ccb ) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1080,7 +1080,7 @@ abort( scsi_sim_cookie cookie, scsi_ccb *ccb_to_abort ) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1093,7 +1093,7 @@ reset_device( scsi_sim_cookie cookie, uchar target_id, uchar target_lun ) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1106,7 +1106,7 @@ term_io( scsi_sim_cookie cookie, scsi_ccb *ccb_to_terminate ) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1119,7 +1119,7 @@ path_inquiry( scsi_sim_cookie cookie, scsi_path_inquiry *inquiry_data ) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1132,7 +1132,7 @@ scan_bus( scsi_sim_cookie cookie ) } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1145,7 +1145,7 @@ reset_bus( scsi_sim_cookie cookie ) } /** - * \fn: + * \fn: * \param : * TODO */ @@ -1156,7 +1156,7 @@ get_restrictions(scsi_sim_cookie cookie, uchar target_id, bool *is_atapi, bool * } /** - * \fn: + * \fn: * \param : * \return: * TODO @@ -1173,41 +1173,41 @@ module_ioctl(scsi_sim_cookie cookie, uint8 targetID, uint32 op, void *buffer, si Declare our module_info so we can be loaded as a kernel module */ static scsi_sim_interface usb_scsi_sim = { - { //driver_module_info + { //driver_module_info { // module_info "busses/scsi/usb/device_v1", // is device_v1 really required? or v1 is enough? - 0, + 0, &std_ops }, - + supports_device, register_device, - init_module, // init_driver, + init_module, // init_driver, uninit_module, // uninit_driver, - + device_removed, device_cleanup, get_supported_paths, }, - + scsi_io, abort, reset_device, term_io, - + path_inquiry, scan_bus, reset_bus, - + get_restrictions, - - module_ioctl //ioctl + + module_ioctl //ioctl }; /** - Export module_info-s list + Export module_info-s list */ _EXPORT module_info *modules[] = { (module_info *) &usb_scsi_sim, diff --git a/src/add-ons/kernel/busses/scsi/usb/usb_scsi.h b/src/add-ons/kernel/busses/scsi/usb/usb_scsi.h index 4bef6bafcf..e86ff3f258 100644 --- a/src/add-ons/kernel/busses/scsi/usb/usb_scsi.h +++ b/src/add-ons/kernel/busses/scsi/usb/usb_scsi.h @@ -1,16 +1,16 @@ /** * * TODO: description - * - * This file is a part of USB SCSI CAM for Haiku OS. + * + * This file is a part of USB SCSI CAM for Haiku. * May be used under terms of the MIT License * * Author(s): * Siarzhuk Zharski - * - * + * + * */ -#ifndef _USB_SCSI_H_ +#ifndef _USB_SCSI_H_ #define _USB_SCSI_H_ #ifndef _OS_H @@ -26,7 +26,7 @@ #endif /*_CAM_H*/ #define MODULE_NAME "usb_scsi" - + #define CONTROLLER_SCSI_BUS 0x00 /* Narrow SCSI bus. Use PI_* to alter this*/ #define MAX_DEVICES_COUNT 0x07 /* simulate Narrow SCSI bus - 8 devices*/ #define CONTROLLER_SCSI_ID 0x07 /* "controller" SCSI ID */ @@ -42,7 +42,7 @@ #define PROTO_MASK 0x0000000f #define PROTO(__value) ((__value) & PROTO_MASK) - + /* command set definitions - are not bitmasks */ #define CMDSET_NONE 0x00000000 #define CMDSET_SCSI 0x00000010 @@ -59,7 +59,7 @@ #define HAS_SET(__mask, __flag) \ (((__mask) & __flag) == (__flag)) -/* fixes - bitmasked */ +/* fixes - bitmasked */ #define FIX_NO_GETMAXLUN 0x00000100 #define FIX_FORCE_RW_TO_6 0x00000200 #define FIX_NO_TEST_UNIT 0x00000400 From afc33db942eed3f9219781eb467500278610fe3a Mon Sep 17 00:00:00 2001 From: Matt Madia Date: Sun, 20 Jan 2013 18:03:31 -0500 Subject: [PATCH 03/86] Launch ReadOnlyBootPrompt if $freshInstallIndicator exists. That file will exist on every read-only media, first boot of writable images (usb,vmdk), and (if installing directly to partition via the build system or a mounted image file) hard disk. The last scenario (of installing directly to hard disk through the build system or mounted image file) may not be ideal, but it generally tends to be an advanced installation method. Additionally, it will occur only on first boot. Fixes #8945. --- data/system/boot/Bootscript | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/data/system/boot/Bootscript b/data/system/boot/Bootscript index 3a52cb2ea2..d0f130ed1b 100644 --- a/data/system/boot/Bootscript +++ b/data/system/boot/Bootscript @@ -117,7 +117,8 @@ if [ "$SAFEMODE" != "yes" ]; then fi # Now ask the user if he wants to run the Installer or continue to the Desktop. -if [ "$isReadOnly" = "yes" ]; then +freshInstallIndicator=/boot/common/settings/fresh_install +if [ "$isReadOnly" = "yes" -o -e $freshInstallIndicator ]; then # Create Installer link (using the write overlay) ln -sf /boot/system/apps/Installer /boot/home/Desktop/Installer @@ -190,7 +191,6 @@ fi # Check for fresh install and run post install scripts. postInstallDir=/boot/common/boot/post_install -freshInstallIndicator=/boot/common/settings/fresh_install if [ -e $freshInstallIndicator ]; then # wait a moment for things to calm down a bit sleep 3 From 2ddbb1e3d2246aada2fd326bb08d1747e3e1d096 Mon Sep 17 00:00:00 2001 From: Alexander von Gluck IV Date: Sun, 20 Jan 2013 22:50:06 +0000 Subject: [PATCH 04/86] networksetup+: Adjust add-on path to match preflet name --- src/tests/kits/net/preflet/NetworkSetupWindow.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/tests/kits/net/preflet/NetworkSetupWindow.cpp b/src/tests/kits/net/preflet/NetworkSetupWindow.cpp index 1750f96a5d..70f566dc8a 100644 --- a/src/tests/kits/net/preflet/NetworkSetupWindow.cpp +++ b/src/tests/kits/net/preflet/NetworkSetupWindow.cpp @@ -259,7 +259,7 @@ NetworkSetupWindow::_BuildShowTabView(int32 msg_what) path.Append(search_path + 3); } else { path.SetTo(search_path); - path.Append("network_setup"); + path.Append("Network Setup"); } search_path = strtok_r(NULL, ":", &next_path_token); From ab372d6fd32fa36704275b58892438dc4590ab0a Mon Sep 17 00:00:00 2001 From: Alexander von Gluck IV Date: Sun, 20 Jan 2013 23:28:08 +0000 Subject: [PATCH 05/86] networksetup+: Simplify media check * Lets just rely on IsWireless and friends in BNetworkInterface as we are checking the same thing twice. --- .../InterfacesAddOn/InterfacesListView.cpp | 24 +++++-------------- 1 file changed, 6 insertions(+), 18 deletions(-) diff --git a/src/tests/kits/net/preflet/InterfacesAddOn/InterfacesListView.cpp b/src/tests/kits/net/preflet/InterfacesAddOn/InterfacesListView.cpp index d41804cf8c..cf64a38342 100644 --- a/src/tests/kits/net/preflet/InterfacesAddOn/InterfacesListView.cpp +++ b/src/tests/kits/net/preflet/InterfacesAddOn/InterfacesListView.cpp @@ -209,25 +209,13 @@ InterfaceListItem::_Init() const char* mediaTypeName = NULL; - int media = fInterface.Media(); + BNetworkDevice device(Name()); + if (device.IsWireless()) + mediaTypeName = "wifi"; + else if (device.IsEthernet()) + mediaTypeName = "ether"; - printf("%s media = 0x%x\n", Name(), media); - switch (IFM_TYPE(media)) { - case IFM_ETHER: - mediaTypeName = "ether"; - break; - case IFM_IEEE80211: - mediaTypeName = "wifi"; - break; - default: { - BNetworkDevice device(Name()); - if (device.IsWireless()) - mediaTypeName = "wifi"; - else if (device.IsEthernet()) - mediaTypeName = "ether"; - break; - } - } + printf("%s is a %s device\n", Name(), mediaTypeName); _PopulateBitmaps(mediaTypeName); // Load the interface icons From 90ae2e54f6ccaca73c011a2aa4cdd660417108ad Mon Sep 17 00:00:00 2001 From: John Scipione Date: Mon, 21 Jan 2013 20:10:59 -0500 Subject: [PATCH 06/86] Update keycodes image with more stylish version --- .../user/keyboard/US_PC_keyboard_keycodes.png | Bin 35608 -> 104275 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/docs/user/keyboard/US_PC_keyboard_keycodes.png b/docs/user/keyboard/US_PC_keyboard_keycodes.png index 134f01213ece3eaf1f6bdcdfcfcbe348a1d44e09..5e81286adbdc7040365a9d30d2ce3045e4064ca2 100644 GIT binary patch literal 104275 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 z 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 P$N&VMu6{1-oD!M<;)ClT literal 35608 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 Date: Tue, 22 Jan 2013 09:16:38 +0100 Subject: [PATCH 07/86] Vim, KeymapSwitcher and UnRAR packages updated * Version of Vim package for x86_64 added; * Version of KeymapSwitcher package for x86_64 added; * KeymapSwitcher package fixed to preserve Cmd <-> Ctrl swap settings on keymaps switch. Fixes #9142; * UnRAR updated from 3.7.8 to 4.2.4, fixed for multibyte characters support and build for x86_64. Partially fixes #4879; --- build/jam/OptionalPackages | 59 +++++++++++++++++++++++++++++++------- 1 file changed, 49 insertions(+), 10 deletions(-) diff --git a/build/jam/OptionalPackages b/build/jam/OptionalPackages index 39525947e4..b0d4a60846 100644 --- a/build/jam/OptionalPackages +++ b/build/jam/OptionalPackages @@ -95,6 +95,7 @@ if $(HAIKU_ADD_ALTERNATIVE_GCC_LIBS) = 1 # TimGMSoundFont - a good quality General MIDI Sound Font # TrackerNewTemplates - template files for Tracker's New menu # Transmission - a fast, easy, and free BitTorrent Client +# UnRAR - utility to list, test and extract RAR archives # UserlandFS - aids native file system development (like FUSE) # Vim - Vi IMproved. Highly configurable text editor # Vision - powerful native IRC client @@ -1330,22 +1331,29 @@ if [ IsOptionalHaikuImagePackageAdded ICU-devel ] { # KeymapSwitcher if [ IsOptionalHaikuImagePackageAdded KeymapSwitcher ] { - if $(TARGET_ARCH) != x86 { - Echo "No optional package KeymapSwitcher available for $(TARGET_ARCH)" ; - } else { + if $(TARGET_ARCH) = x86 { if $(HAIKU_GCC_VERSION[1]) >= 4 { InstallOptionalHaikuImagePackage - KeymapSwitcher-1.2.7-r1a4-x86-gcc4-2012-11-01.zip - : $(baseURL)/KeymapSwitcher-1.2.7-r1a4-x86-gcc4-2012-11-01.zip + KeymapSwitcher-1.2.7-x86-gcc4-2013-01-08.zip + : $(baseURL)/KeymapSwitcher-1.2.7-x86-gcc4-2013-01-08.zip : : : false ; } else { InstallOptionalHaikuImagePackage - KeymapSwitcher-1.2.7-r1a4-x86-gcc2-2012-11-01.zip - : $(baseURL)/KeymapSwitcher-1.2.7-r1a4-x86-gcc2-2012-11-01.zip + KeymapSwitcher-1.2.7-x86-gcc2-2013-01-08.zip + : $(baseURL)/KeymapSwitcher-1.2.7-x86-gcc2-2013-01-08.zip : : : false ; } AddSymlinkToHaikuImage home config settings deskbar Preferences : /boot/common/bin/KeymapSwitcher ; + } else if $(TARGET_ARCH) = x86_64 { + InstallOptionalHaikuImagePackage + KeymapSwitcher-1.2.7-x86_64-2013-01-08.zip + : $(baseURL)/KeymapSwitcher-1.2.7-x86_64-2013-01-08.zip + : : true ; + AddSymlinkToHaikuImage home config settings deskbar Preferences + : /boot/common/bin/KeymapSwitcher ; + } else { + Echo "No optional package KeymapSwitcher available for $(TARGET_ARCH)" ; } } @@ -2080,6 +2088,31 @@ if [ IsOptionalHaikuImagePackageAdded Transmission ] { } +# UnRAR +if [ IsOptionalHaikuImagePackageAdded UnRAR ] { + if $(TARGET_ARCH) = x86 { + if $(HAIKU_GCC_VERSION[1]) >= 4 { + InstallOptionalHaikuImagePackage + UnRAR-4.2.4-x86-gcc4-2013-01-21.zip + : $(baseURL)/UnRAR-4.2.4-x86-gcc4-2013-01-21.zip + : : true ; + } else { + InstallOptionalHaikuImagePackage + UnRAR-4.2.4-x86-gcc2-2013-01-21.zip + : $(baseURL)/UnRAR-4.2.4-x86-gcc2-2013-01-21.zip + : : true ; + } + } else if $(TARGET_ARCH) = x86_64 { + InstallOptionalHaikuImagePackage + UnRAR-4.2.4-x86_64-2013-01-21.zip + : $(baseURL)/UnRAR-4.2.4-x86_64-2013-01-21.zip + : : true ; + } else { + Echo "No optional package UnRAR available for $(TARGET_ARCH)" ; + } +} + + # UserlandFS if [ IsOptionalHaikuImagePackageAdded UserlandFS ] { local arch = $(TARGET_ARCH) ; @@ -2135,9 +2168,7 @@ if [ IsOptionalHaikuImagePackageAdded UserlandFS ] { # Vim if [ IsOptionalHaikuImagePackageAdded Vim ] { - if $(TARGET_ARCH) != x86 { - Echo "No optional package Vim available for $(TARGET_ARCH)" ; - } else { + if $(TARGET_ARCH) = x86 { if $(HAIKU_GCC_VERSION[1]) >= 4 { InstallOptionalHaikuImagePackage vim-7.3-r1a4-x86-gcc4-2012-09-26.zip : $(baseURL)/vim-7.3-r1a4-x86-gcc4-2012-09-26.zip @@ -2149,6 +2180,14 @@ if [ IsOptionalHaikuImagePackageAdded Vim ] { } AddSymlinkToHaikuImage home config settings deskbar Applications : /boot/common/bin/gvim ; + } else if $(TARGET_ARCH) = x86_64 { + InstallOptionalHaikuImagePackage vim-7.3-x86_64-2013-01-19.zip + : $(baseURL)/vim-7.3-x86_64-2013-01-19.zip + : : true ; + AddSymlinkToHaikuImage home config settings deskbar Applications + : /boot/common/bin/gvim ; + } else { + Echo "No optional package Vim available for $(TARGET_ARCH)" ; } } From e449bae89186bea95f123280559c5195be5017e7 Mon Sep 17 00:00:00 2001 From: Siarzhuk Zharski Date: Tue, 22 Jan 2013 09:27:44 +0100 Subject: [PATCH 08/86] bin/unrar outsorced to UnRAR 4.2.4 opt.package --- build/jam/HaikuImage | 2 +- src/bin/Jamfile | 1 - src/bin/unrar/Jamfile | 47 - src/bin/unrar/arccmt.cpp | 215 --- src/bin/unrar/archive.cpp | 267 ---- src/bin/unrar/archive.hpp | 126 -- src/bin/unrar/arcread.cpp | 653 ---------- src/bin/unrar/array.hpp | 122 -- src/bin/unrar/beosea.cpp | 113 -- src/bin/unrar/cmddata.cpp | 1287 ------------------ src/bin/unrar/cmddata.hpp | 57 - src/bin/unrar/coder.cpp | 47 - src/bin/unrar/coder.hpp | 24 - src/bin/unrar/compress.hpp | 36 - src/bin/unrar/consio.cpp | 289 ---- src/bin/unrar/consio.hpp | 46 - src/bin/unrar/crc.cpp | 61 - src/bin/unrar/crc.hpp | 10 - src/bin/unrar/crypt.cpp | 381 ------ src/bin/unrar/crypt.hpp | 62 - src/bin/unrar/dll.cpp | 365 ------ src/bin/unrar/dll.def | 12 - src/bin/unrar/dll.hpp | 138 -- src/bin/unrar/encname.cpp | 57 - src/bin/unrar/encname.hpp | 20 - src/bin/unrar/errhnd.cpp | 374 ------ src/bin/unrar/errhnd.hpp | 62 - src/bin/unrar/extinfo.cpp | 76 -- src/bin/unrar/extinfo.hpp | 8 - src/bin/unrar/extract.cpp | 873 ------------- src/bin/unrar/extract.hpp | 42 - src/bin/unrar/filcreat.cpp | 239 ---- src/bin/unrar/filcreat.hpp | 13 - src/bin/unrar/file.cpp | 704 ---------- src/bin/unrar/file.hpp | 100 -- src/bin/unrar/filefn.cpp | 570 -------- src/bin/unrar/filefn.hpp | 41 - src/bin/unrar/filestr.cpp | 145 --- src/bin/unrar/filestr.hpp | 8 - src/bin/unrar/find.cpp | 296 ----- src/bin/unrar/find.hpp | 48 - src/bin/unrar/getbits.cpp | 24 - src/bin/unrar/getbits.hpp | 38 - src/bin/unrar/global.cpp | 4 - src/bin/unrar/global.hpp | 14 - src/bin/unrar/headers.hpp | 306 ----- src/bin/unrar/int64.cpp | 274 ---- src/bin/unrar/int64.hpp | 86 -- src/bin/unrar/isnt.cpp | 17 - src/bin/unrar/isnt.hpp | 6 - src/bin/unrar/license.txt | 40 - src/bin/unrar/list.cpp | 388 ------ src/bin/unrar/list.hpp | 6 - src/bin/unrar/loclang.hpp | 349 ----- src/bin/unrar/log.cpp | 24 - src/bin/unrar/log.hpp | 18 - src/bin/unrar/match.cpp | 262 ---- src/bin/unrar/match.hpp | 12 - src/bin/unrar/model.cpp | 610 --------- src/bin/unrar/model.hpp | 132 -- src/bin/unrar/msc.dep | 2532 ------------------------------------ src/bin/unrar/options.cpp | 28 - src/bin/unrar/options.hpp | 142 -- src/bin/unrar/os.hpp | 246 ---- src/bin/unrar/os2ea.cpp | 94 -- src/bin/unrar/pathfn.cpp | 714 ---------- src/bin/unrar/pathfn.hpp | 46 - src/bin/unrar/rar.cpp | 144 -- src/bin/unrar/rar.hpp | 80 -- src/bin/unrar/rardefs.hpp | 24 - src/bin/unrar/rarfn.hpp | 7 - src/bin/unrar/rarlang.hpp | 10 - src/bin/unrar/raros.hpp | 41 - src/bin/unrar/rartypes.hpp | 23 - src/bin/unrar/rarvm.cpp | 1113 ---------------- src/bin/unrar/rarvm.hpp | 109 -- src/bin/unrar/rarvmtbl.cpp | 53 - src/bin/unrar/rawread.cpp | 126 -- src/bin/unrar/rawread.hpp | 32 - src/bin/unrar/rdwrfn.cpp | 264 ---- src/bin/unrar/rdwrfn.hpp | 83 -- src/bin/unrar/readme.txt | 63 - src/bin/unrar/recvol.cpp | 367 ------ src/bin/unrar/recvol.hpp | 16 - src/bin/unrar/resource.cpp | 12 - src/bin/unrar/resource.hpp | 14 - src/bin/unrar/rijndael.cpp | 298 ----- src/bin/unrar/rijndael.hpp | 37 - src/bin/unrar/rs.cpp | 143 -- src/bin/unrar/rs.hpp | 32 - src/bin/unrar/savepos.cpp | 15 - src/bin/unrar/savepos.hpp | 15 - src/bin/unrar/scantree.cpp | 292 ----- src/bin/unrar/scantree.hpp | 52 - src/bin/unrar/sha1.cpp | 231 ---- src/bin/unrar/sha1.hpp | 17 - src/bin/unrar/smallfn.cpp | 23 - src/bin/unrar/smallfn.hpp | 8 - src/bin/unrar/strfn.cpp | 199 --- src/bin/unrar/strfn.hpp | 34 - src/bin/unrar/strlist.cpp | 191 --- src/bin/unrar/strlist.hpp | 39 - src/bin/unrar/suballoc.cpp | 258 ---- src/bin/unrar/suballoc.hpp | 87 -- src/bin/unrar/system.cpp | 96 -- src/bin/unrar/system.hpp | 26 - src/bin/unrar/timefn.cpp | 288 ---- src/bin/unrar/timefn.hpp | 57 - src/bin/unrar/ulinks.cpp | 32 - src/bin/unrar/ulinks.hpp | 9 - src/bin/unrar/unicode.cpp | 493 ------- src/bin/unrar/unicode.hpp | 82 -- src/bin/unrar/unios2.cpp | 128 -- src/bin/unrar/unpack.cpp | 1004 -------------- src/bin/unrar/unpack.hpp | 217 --- src/bin/unrar/unpack15.cpp | 511 -------- src/bin/unrar/unpack20.cpp | 370 ------ src/bin/unrar/unrar.rdef | 13 - src/bin/unrar/uowners.cpp | 80 -- src/bin/unrar/version.hpp | 6 - src/bin/unrar/volume.cpp | 221 ---- src/bin/unrar/volume.hpp | 11 - src/bin/unrar/win32acl.cpp | 127 -- src/bin/unrar/win32stm.cpp | 154 --- 124 files changed, 1 insertion(+), 22925 deletions(-) delete mode 100644 src/bin/unrar/Jamfile delete mode 100644 src/bin/unrar/arccmt.cpp delete mode 100644 src/bin/unrar/archive.cpp delete mode 100644 src/bin/unrar/archive.hpp delete mode 100644 src/bin/unrar/arcread.cpp delete mode 100644 src/bin/unrar/array.hpp delete mode 100644 src/bin/unrar/beosea.cpp delete mode 100644 src/bin/unrar/cmddata.cpp delete mode 100644 src/bin/unrar/cmddata.hpp delete mode 100644 src/bin/unrar/coder.cpp delete mode 100644 src/bin/unrar/coder.hpp delete mode 100644 src/bin/unrar/compress.hpp delete mode 100644 src/bin/unrar/consio.cpp delete mode 100644 src/bin/unrar/consio.hpp delete mode 100644 src/bin/unrar/crc.cpp delete mode 100644 src/bin/unrar/crc.hpp delete mode 100644 src/bin/unrar/crypt.cpp delete mode 100644 src/bin/unrar/crypt.hpp delete mode 100644 src/bin/unrar/dll.cpp delete mode 100644 src/bin/unrar/dll.def delete mode 100644 src/bin/unrar/dll.hpp delete mode 100644 src/bin/unrar/encname.cpp delete mode 100644 src/bin/unrar/encname.hpp delete mode 100644 src/bin/unrar/errhnd.cpp delete mode 100644 src/bin/unrar/errhnd.hpp delete mode 100644 src/bin/unrar/extinfo.cpp delete mode 100644 src/bin/unrar/extinfo.hpp delete mode 100644 src/bin/unrar/extract.cpp delete mode 100644 src/bin/unrar/extract.hpp delete mode 100644 src/bin/unrar/filcreat.cpp delete mode 100644 src/bin/unrar/filcreat.hpp delete mode 100644 src/bin/unrar/file.cpp delete mode 100644 src/bin/unrar/file.hpp delete mode 100644 src/bin/unrar/filefn.cpp delete mode 100644 src/bin/unrar/filefn.hpp delete mode 100644 src/bin/unrar/filestr.cpp delete mode 100644 src/bin/unrar/filestr.hpp delete mode 100644 src/bin/unrar/find.cpp delete mode 100644 src/bin/unrar/find.hpp delete mode 100644 src/bin/unrar/getbits.cpp delete mode 100644 src/bin/unrar/getbits.hpp delete mode 100644 src/bin/unrar/global.cpp delete mode 100644 src/bin/unrar/global.hpp delete mode 100644 src/bin/unrar/headers.hpp delete mode 100644 src/bin/unrar/int64.cpp delete mode 100644 src/bin/unrar/int64.hpp delete mode 100644 src/bin/unrar/isnt.cpp delete mode 100644 src/bin/unrar/isnt.hpp delete mode 100644 src/bin/unrar/license.txt delete mode 100644 src/bin/unrar/list.cpp delete mode 100644 src/bin/unrar/list.hpp delete mode 100644 src/bin/unrar/loclang.hpp delete mode 100644 src/bin/unrar/log.cpp delete mode 100644 src/bin/unrar/log.hpp delete mode 100644 src/bin/unrar/match.cpp delete mode 100644 src/bin/unrar/match.hpp delete mode 100644 src/bin/unrar/model.cpp delete mode 100644 src/bin/unrar/model.hpp delete mode 100644 src/bin/unrar/msc.dep delete mode 100644 src/bin/unrar/options.cpp delete mode 100644 src/bin/unrar/options.hpp delete mode 100644 src/bin/unrar/os.hpp delete mode 100644 src/bin/unrar/os2ea.cpp delete mode 100644 src/bin/unrar/pathfn.cpp delete mode 100644 src/bin/unrar/pathfn.hpp delete mode 100644 src/bin/unrar/rar.cpp delete mode 100644 src/bin/unrar/rar.hpp delete mode 100644 src/bin/unrar/rardefs.hpp delete mode 100644 src/bin/unrar/rarfn.hpp delete mode 100644 src/bin/unrar/rarlang.hpp delete mode 100644 src/bin/unrar/raros.hpp delete mode 100644 src/bin/unrar/rartypes.hpp delete mode 100644 src/bin/unrar/rarvm.cpp delete mode 100644 src/bin/unrar/rarvm.hpp delete mode 100644 src/bin/unrar/rarvmtbl.cpp delete mode 100644 src/bin/unrar/rawread.cpp delete mode 100644 src/bin/unrar/rawread.hpp delete mode 100644 src/bin/unrar/rdwrfn.cpp delete mode 100644 src/bin/unrar/rdwrfn.hpp delete mode 100644 src/bin/unrar/readme.txt delete mode 100644 src/bin/unrar/recvol.cpp delete mode 100644 src/bin/unrar/recvol.hpp delete mode 100644 src/bin/unrar/resource.cpp delete mode 100644 src/bin/unrar/resource.hpp delete mode 100644 src/bin/unrar/rijndael.cpp delete mode 100644 src/bin/unrar/rijndael.hpp delete mode 100644 src/bin/unrar/rs.cpp delete mode 100644 src/bin/unrar/rs.hpp delete mode 100644 src/bin/unrar/savepos.cpp delete mode 100644 src/bin/unrar/savepos.hpp delete mode 100644 src/bin/unrar/scantree.cpp delete mode 100644 src/bin/unrar/scantree.hpp delete mode 100644 src/bin/unrar/sha1.cpp delete mode 100644 src/bin/unrar/sha1.hpp delete mode 100644 src/bin/unrar/smallfn.cpp delete mode 100644 src/bin/unrar/smallfn.hpp delete mode 100644 src/bin/unrar/strfn.cpp delete mode 100644 src/bin/unrar/strfn.hpp delete mode 100644 src/bin/unrar/strlist.cpp delete mode 100644 src/bin/unrar/strlist.hpp delete mode 100644 src/bin/unrar/suballoc.cpp delete mode 100644 src/bin/unrar/suballoc.hpp delete mode 100644 src/bin/unrar/system.cpp delete mode 100644 src/bin/unrar/system.hpp delete mode 100644 src/bin/unrar/timefn.cpp delete mode 100644 src/bin/unrar/timefn.hpp delete mode 100644 src/bin/unrar/ulinks.cpp delete mode 100644 src/bin/unrar/ulinks.hpp delete mode 100644 src/bin/unrar/unicode.cpp delete mode 100644 src/bin/unrar/unicode.hpp delete mode 100644 src/bin/unrar/unios2.cpp delete mode 100644 src/bin/unrar/unpack.cpp delete mode 100644 src/bin/unrar/unpack.hpp delete mode 100644 src/bin/unrar/unpack15.cpp delete mode 100644 src/bin/unrar/unpack20.cpp delete mode 100644 src/bin/unrar/unrar.rdef delete mode 100644 src/bin/unrar/uowners.cpp delete mode 100644 src/bin/unrar/version.hpp delete mode 100644 src/bin/unrar/volume.cpp delete mode 100644 src/bin/unrar/volume.hpp delete mode 100644 src/bin/unrar/win32acl.cpp delete mode 100644 src/bin/unrar/win32stm.cpp diff --git a/build/jam/HaikuImage b/build/jam/HaikuImage index a90dca68ca..3dddaaf1b3 100644 --- a/build/jam/HaikuImage +++ b/build/jam/HaikuImage @@ -35,7 +35,7 @@ SYSTEM_BIN = [ FFilterByBuildFeatures split stat strace stty su sum sync sysinfo tac tail tcpdump tcptester tee telnet telnetd test timeout top touch tput tr traceroute translate trash true truncate tsort tty - uname unchop unexpand unmount uniq unlink unrar unshar unzip unzipsfx + uname unchop unexpand unmount uniq unlink unshar unzip unzipsfx updatedb uptime urlwrapper useradd uudecode uuencode vdir version vmstat waitfor watch wc wget whoami writembr@x86 xargs xres yes diff --git a/src/bin/Jamfile b/src/bin/Jamfile index dccce63da5..4d1f6530bb 100644 --- a/src/bin/Jamfile +++ b/src/bin/Jamfile @@ -274,7 +274,6 @@ SubInclude HAIKU_TOP src bin rmd160 ; SubInclude HAIKU_TOP src bin screen_blanker ; SubInclude HAIKU_TOP src bin screenmode ; SubInclude HAIKU_TOP src bin sharutils ; -SubInclude HAIKU_TOP src bin unrar ; SubInclude HAIKU_TOP src bin writembr ; SubInclude HAIKU_TOP src bin zic ; diff --git a/src/bin/unrar/Jamfile b/src/bin/unrar/Jamfile deleted file mode 100644 index b7a0dce075..0000000000 --- a/src/bin/unrar/Jamfile +++ /dev/null @@ -1,47 +0,0 @@ -SubDir HAIKU_TOP src bin unrar ; - -BinCommand unrar : - rar.cpp - strlist.cpp - strfn.cpp - pathfn.cpp - int64.cpp - savepos.cpp - global.cpp - file.cpp - filefn.cpp - filcreat.cpp - archive.cpp - arcread.cpp - unicode.cpp - system.cpp - isnt.cpp - crypt.cpp - crc.cpp - rawread.cpp - encname.cpp - resource.cpp - match.cpp - timefn.cpp - rdwrfn.cpp - consio.cpp - options.cpp - ulinks.cpp - errhnd.cpp - rarvm.cpp - rijndael.cpp - getbits.cpp - sha1.cpp - extinfo.cpp - extract.cpp - volume.cpp - list.cpp - find.cpp - unpack.cpp - cmddata.cpp - scantree.cpp - filestr.cpp - recvol.cpp - rs.cpp - : be $(TARGET_LIBSUPC++) : unrar.rdef -; diff --git a/src/bin/unrar/arccmt.cpp b/src/bin/unrar/arccmt.cpp deleted file mode 100644 index 6ada2f03c4..0000000000 --- a/src/bin/unrar/arccmt.cpp +++ /dev/null @@ -1,215 +0,0 @@ -bool Archive::GetComment(Array *CmtData,Array *CmtDataW) -{ - if (!MainComment) - return(false); - SaveFilePos SavePos(*this); - - ushort CmtLength; -#ifndef SFX_MODULE - if (OldFormat) - { - Seek(SFXSize+SIZEOF_OLDMHD,SEEK_SET); - CmtLength=GetByte()+(GetByte()<<8); - } - else -#endif - { - if (NewMhd.Flags & MHD_COMMENT) - { - Seek(SFXSize+SIZEOF_MARKHEAD+SIZEOF_NEWMHD,SEEK_SET); - ReadHeader(); - } - else - { - Seek(SFXSize+SIZEOF_MARKHEAD+NewMhd.HeadSize,SEEK_SET); - return(SearchSubBlock(SUBHEAD_TYPE_CMT)!=0 && ReadCommentData(CmtData,CmtDataW)!=0); - } -#ifndef SFX_MODULE - if (CommHead.HeadCRC!=HeaderCRC) - { - Log(FileName,St(MLogCommHead)); - Alarm(); - return(false); - } - CmtLength=CommHead.HeadSize-SIZEOF_COMMHEAD; -#endif - } -#ifndef SFX_MODULE - if (OldFormat && (OldMhd.Flags & MHD_PACK_COMMENT) || !OldFormat && CommHead.Method!=0x30) - { - if (!OldFormat && (CommHead.UnpVer < 15 || CommHead.UnpVer > UNP_VER || CommHead.Method > 0x35)) - return(false); - ComprDataIO DataIO; - Unpack Unpack(&DataIO); - Unpack.Init(); - DataIO.SetTestMode(true); - uint UnpCmtLength; - if (OldFormat) - { -#ifdef NOCRYPT - return(false); -#else - UnpCmtLength=GetByte()+(GetByte()<<8); - CmtLength-=2; - DataIO.SetCmt13Encryption(); -#endif - } - else - UnpCmtLength=CommHead.UnpSize; - DataIO.SetFiles(this,NULL); - DataIO.EnableShowProgress(false); - DataIO.SetPackedSizeToRead(CmtLength); - Unpack.SetDestSize(UnpCmtLength); - Unpack.DoUnpack(CommHead.UnpVer,false); - - if (!OldFormat && ((~DataIO.UnpFileCRC)&0xffff)!=CommHead.CommCRC) - { - Log(FileName,St(MLogCommBrk)); - Alarm(); - return(false); - } - else - { - unsigned char *UnpData; - uint UnpDataSize; - DataIO.GetUnpackedData(&UnpData,&UnpDataSize); - CmtData->Alloc(UnpDataSize); - memcpy(&((*CmtData)[0]),UnpData,UnpDataSize); - } - } - else - { - CmtData->Alloc(CmtLength); - - Read(&((*CmtData)[0]),CmtLength); - if (!OldFormat && CommHead.CommCRC!=(~CRC(0xffffffff,&((*CmtData)[0]),CmtLength)&0xffff)) - { - Log(FileName,St(MLogCommBrk)); - Alarm(); - CmtData->Reset(); - return(false); - } - } -#endif -#if defined(_WIN_32) && !defined(_WIN_CE) - if (CmtData->Size()>0) - { - int CmtSize=CmtData->Size(); - OemToCharBuff((char *)CmtData->Addr(),(char *)CmtData->Addr(),CmtSize); - - if (CmtDataW!=NULL) - { - CmtDataW->Alloc(CmtSize+1); - CmtData->Push(0); - CharToWide((char *)CmtData->Addr(),CmtDataW->Addr(),CmtSize+1); - CmtData->Alloc(CmtSize); - CmtDataW->Alloc(strlenw(CmtDataW->Addr())); - } - } -#endif - return(CmtData->Size()>0); -} - - -int Archive::ReadCommentData(Array *CmtData,Array *CmtDataW) -{ - bool Unicode=SubHead.SubFlags & SUBHEAD_FLAGS_CMT_UNICODE; - if (!ReadSubData(CmtData,NULL)) - return(0); - int CmtSize=CmtData->Size(); - if (Unicode) - { - CmtSize/=2; - Array DataW(CmtSize+1); - RawToWide(CmtData->Addr(),DataW.Addr(),CmtSize); - DataW[CmtSize]=0; - int DestSize=CmtSize*4; - CmtData->Alloc(DestSize+1); - WideToChar(DataW.Addr(),(char *)CmtData->Addr(),DestSize); - (*CmtData)[DestSize]=0; - CmtSize=strlen((char *)CmtData->Addr()); - CmtData->Alloc(CmtSize); - if (CmtDataW!=NULL) - { - *CmtDataW=DataW; - CmtDataW->Alloc(CmtSize); - } - } - else - if (CmtDataW!=NULL) - { - CmtData->Push(0); - CmtDataW->Alloc(CmtSize+1); - CharToWide((char *)CmtData->Addr(),CmtDataW->Addr(),CmtSize+1); - CmtData->Alloc(CmtSize); - CmtDataW->Alloc(strlenw(CmtDataW->Addr())); - } - return(CmtSize); -} - - -void Archive::ViewComment() -{ -#ifndef GUI - if (Cmd->DisableComment) - return; - Array CmtBuf; - if (GetComment(&CmtBuf,NULL)) - { - int CmtSize=CmtBuf.Size(); - char *ChPtr=(char *)memchr(&CmtBuf[0],0x1A,CmtSize); - if (ChPtr!=NULL) - CmtSize=ChPtr-(char *)&CmtBuf[0]; - mprintf("\n"); - OutComment((char *)&CmtBuf[0],CmtSize); - } -#endif -} - - -#ifndef SFX_MODULE -void Archive::ViewFileComment() -{ - if (!(NewLhd.Flags & LHD_COMMENT) || Cmd->DisableComment || OldFormat) - return; -#ifndef GUI - mprintf(St(MFileComment)); -#endif - const int MaxSize=0x8000; - Array CmtBuf(MaxSize); - SaveFilePos SavePos(*this); - Seek(CurBlockPos+SIZEOF_NEWLHD+NewLhd.NameSize,SEEK_SET); - Int64 SaveCurBlockPos=CurBlockPos; - Int64 SaveNextBlockPos=NextBlockPos; - - int Size=ReadHeader(); - - CurBlockPos=SaveCurBlockPos; - NextBlockPos=SaveNextBlockPos; - - if (Size<7 || CommHead.HeadType!=COMM_HEAD) - return; - if (CommHead.HeadCRC!=HeaderCRC) - { -#ifndef GUI - Log(FileName,St(MLogCommHead)); -#endif - return; - } - if (CommHead.UnpVer < 15 || CommHead.UnpVer > UNP_VER || - CommHead.Method > 0x30 || CommHead.UnpSize > MaxSize) - return; - Read(&CmtBuf[0],CommHead.UnpSize); - if (CommHead.CommCRC!=((~CRC(0xffffffff,&CmtBuf[0],CommHead.UnpSize)&0xffff))) - { - Log(FileName,St(MLogBrokFCmt)); - } - else - { - OutComment(&CmtBuf[0],CommHead.UnpSize); -#ifndef GUI - mprintf("\n"); -#endif - } -} -#endif diff --git a/src/bin/unrar/archive.cpp b/src/bin/unrar/archive.cpp deleted file mode 100644 index 3460f993ef..0000000000 --- a/src/bin/unrar/archive.cpp +++ /dev/null @@ -1,267 +0,0 @@ -#include "rar.hpp" - -#ifndef SHELL_EXT -#include "arccmt.cpp" -#endif - - -Archive::Archive(RAROptions *InitCmd) -{ - Cmd=InitCmd==NULL ? &DummyCmd:InitCmd; - OpenShared=Cmd->OpenShared; - OldFormat=false; - Solid=false; - Volume=false; - MainComment=false; - Locked=false; - Signed=false; - NotFirstVolume=false; - SFXSize=0; - LatestTime.Reset(); - Protected=false; - Encrypted=false; - BrokenFileHeader=false; - LastReadBlock=0; - - CurBlockPos=0; - NextBlockPos=0; - - RecoveryPos=SIZEOF_MARKHEAD; - RecoverySectors=-1; - - memset(&NewMhd,0,sizeof(NewMhd)); - NewMhd.HeadType=MAIN_HEAD; - NewMhd.HeadSize=SIZEOF_NEWMHD; - HeaderCRC=0; - VolWrite=0; - AddingFilesSize=0; - AddingHeadersSize=0; -#if !defined(SHELL_EXT) && !defined(NOCRYPT) - *HeadersSalt=0; - *SubDataSalt=0; -#endif - *FirstVolumeName=0; - *FirstVolumeNameW=0; - - Splitting=false; - NewArchive=false; - - SilentOpen=false; - -} - - -#ifndef SHELL_EXT -void Archive::CheckArc(bool EnableBroken) -{ - if (!IsArchive(EnableBroken)) - { - Log(FileName,St(MBadArc),FileName); - ErrHandler.Exit(FATAL_ERROR); - } -} -#endif - - -#if !defined(SHELL_EXT) && !defined(SFX_MODULE) -void Archive::CheckOpen(char *Name,wchar *NameW) -{ - TOpen(Name,NameW); - CheckArc(false); -} -#endif - - -bool Archive::WCheckOpen(char *Name,wchar *NameW) -{ - if (!WOpen(Name,NameW)) - return(false); - if (!IsArchive(false)) - { -#ifndef SHELL_EXT - Log(FileName,St(MNotRAR),FileName); -#endif - Close(); - return(false); - } - return(true); -} - - -bool Archive::IsSignature(byte *D) -{ - bool Valid=false; - if (D[0]==0x52) -#ifndef SFX_MODULE - if (D[1]==0x45 && D[2]==0x7e && D[3]==0x5e) - { - OldFormat=true; - Valid=true; - } - else -#endif - if (D[1]==0x61 && D[2]==0x72 && D[3]==0x21 && D[4]==0x1a && D[5]==0x07 && D[6]==0x00) - { - OldFormat=false; - Valid=true; - } - return(Valid); -} - - -bool Archive::IsArchive(bool EnableBroken) -{ - Encrypted=false; -#ifndef SFX_MODULE - if (IsDevice()) - { -#ifndef SHELL_EXT - Log(FileName,St(MInvalidName),FileName); -#endif - return(false); - } -#endif - if (Read(MarkHead.Mark,SIZEOF_MARKHEAD)!=SIZEOF_MARKHEAD) - return(false); - SFXSize=0; - if (IsSignature(MarkHead.Mark)) - { - if (OldFormat) - Seek(0,SEEK_SET); - } - else - { - Array Buffer(MAXSFXSIZE); - long CurPos=int64to32(Tell()); - int ReadSize=Read(&Buffer[0],Buffer.Size()-16); - for (int I=0;I0 && CurPos<28 && ReadSize>31) - { - char *D=&Buffer[28-CurPos]; - if (D[0]!=0x52 || D[1]!=0x53 || D[2]!=0x46 || D[3]!=0x58) - continue; - } - SFXSize=CurPos+I; - Seek(SFXSize,SEEK_SET); - if (!OldFormat) - Read(MarkHead.Mark,SIZEOF_MARKHEAD); - break; - } - if (SFXSize==0) - return(false); - } - ReadHeader(); - SeekToNext(); -#ifndef SFX_MODULE - if (OldFormat) - { - NewMhd.Flags=OldMhd.Flags & 0x3f; - NewMhd.HeadSize=OldMhd.HeadSize; - } - else -#endif - { - if (HeaderCRC!=NewMhd.HeadCRC) - { -#ifndef SHELL_EXT - Log(FileName,St(MLogMainHead)); -#endif - Alarm(); - if (!EnableBroken) - return(false); - } - } - Volume=(NewMhd.Flags & MHD_VOLUME); - Solid=(NewMhd.Flags & MHD_SOLID)!=0; - MainComment=(NewMhd.Flags & MHD_COMMENT)!=0; - Locked=(NewMhd.Flags & MHD_LOCK)!=0; - Signed=(NewMhd.PosAV!=0); - Protected=(NewMhd.Flags & MHD_PROTECT)!=0; - Encrypted=(NewMhd.Flags & MHD_PASSWORD)!=0; - - if (NewMhd.EncryptVer>UNP_VER) - { -#ifdef RARDLL - Cmd->DllError=ERAR_UNKNOWN_FORMAT; -#else - ErrHandler.SetErrorCode(WARNING); - #if !defined(SILENT) && !defined(SFX_MODULE) - Log(FileName,St(MUnknownMeth),FileName); - Log(FileName,St(MVerRequired),NewMhd.EncryptVer/10,NewMhd.EncryptVer%10); - #endif -#endif - return(false); - } -#ifdef RARDLL - SilentOpen=true; -#endif - - //if not encrypted, we'll check it below - NotFirstVolume=Encrypted && (NewMhd.Flags & MHD_FIRSTVOLUME)==0; - - if (!SilentOpen || !Encrypted) - { - SaveFilePos SavePos(*this); - Int64 SaveCurBlockPos=CurBlockPos,SaveNextBlockPos=NextBlockPos; - - NotFirstVolume=false; - while (ReadHeader()) - { - int HeaderType=GetHeaderType(); - if (HeaderType==NEWSUB_HEAD) - { - if (SubHead.CmpName(SUBHEAD_TYPE_CMT)) - MainComment=true; - if ((SubHead.Flags & LHD_SPLIT_BEFORE) || - Volume && (NewMhd.Flags & MHD_FIRSTVOLUME)==0) - NotFirstVolume=true; - } - else - { - if (HeaderType==FILE_HEAD && ((NewLhd.Flags & LHD_SPLIT_BEFORE)!=0 || - Volume && NewLhd.UnpVer>=29 && (NewMhd.Flags & MHD_FIRSTVOLUME)==0)) - NotFirstVolume=true; - break; - } - SeekToNext(); - } - CurBlockPos=SaveCurBlockPos; - NextBlockPos=SaveNextBlockPos; - } - if (!Volume || !NotFirstVolume) - { - strcpy(FirstVolumeName,FileName); - strcpyw(FirstVolumeNameW,FileNameW); - } - - return(true); -} - - - - -void Archive::SeekToNext() -{ - Seek(NextBlockPos,SEEK_SET); -} - - -#ifndef SFX_MODULE -int Archive::GetRecoverySize(bool Required) -{ - if (!Protected) - return(0); - if (RecoverySectors!=-1 || !Required) - return(RecoverySectors); - SaveFilePos SavePos(*this); - Seek(SFXSize,SEEK_SET); - SearchSubBlock(SUBHEAD_TYPE_RR); - return(RecoverySectors); -} -#endif - - - - diff --git a/src/bin/unrar/archive.hpp b/src/bin/unrar/archive.hpp deleted file mode 100644 index 1e0675e759..0000000000 --- a/src/bin/unrar/archive.hpp +++ /dev/null @@ -1,126 +0,0 @@ -#ifndef _RAR_ARCHIVE_ -#define _RAR_ARCHIVE_ - -class Pack; - -enum {EN_LOCK=1,EN_VOL=2,EN_FIRSTVOL=4}; - -class Archive:public File -{ - private: - bool IsSignature(byte *D); - void UpdateLatestTime(FileHeader *CurBlock); - void ConvertNameCase(char *Name); - void ConvertNameCase(wchar *Name); - void ConvertUnknownHeader(); - int ReadOldHeader(); - void PrepareExtraTime(FileHeader *hd,EXTTIME_MODE etm,EXTTIME_MODE etc,EXTTIME_MODE eta,EXTTIME_MODE etarc,Array &TimeData); - -#if !defined(SHELL_EXT) && !defined(NOCRYPT) - CryptData HeadersCrypt; - byte HeadersSalt[SALT_SIZE]; -#endif -#ifndef SHELL_EXT - ComprDataIO SubDataIO; - byte SubDataSalt[SALT_SIZE]; -#endif - RAROptions *Cmd,DummyCmd; - - MarkHeader MarkHead; - OldMainHeader OldMhd; - - int RecoverySectors; - Int64 RecoveryPos; - - RarTime LatestTime; - int LastReadBlock; - int CurHeaderType; - - bool SilentOpen; - public: - Archive(RAROptions *InitCmd=NULL); - bool IsArchive(bool EnableBroken); - int SearchBlock(int BlockType); - int SearchSubBlock(const char *Type); - int ReadBlock(int BlockType); - void WriteBlock(int BlockType,BaseBlock *wb=NULL); - int PrepareNamesToWrite(char *Name,wchar *NameW,char *DestName,byte *DestNameW); - void SetLhdSize(); - int ReadHeader(); - void CheckArc(bool EnableBroken); - void CheckOpen(char *Name,wchar *NameW=NULL); - bool WCheckOpen(char *Name,wchar *NameW=NULL); - bool TestLock(int Mode); - void MakeTemp(); - void CopyMainHeader(Archive &Src,bool CopySFX=true,char *NameToDisplay=NULL); - bool ProcessToFileHead(Archive &Src,bool LastBlockAdded, - Pack *Pack=NULL,const char *SkipName=NULL); - void TmpToArc(Archive &Src); - void CloseNew(int AdjustRecovery,bool CloseVolume); - void WriteEndBlock(bool CloseVolume); - void CopyFileRecord(Archive &Src); - void CopyArchiveData(Archive &Src); - bool GetComment(Array *CmtData,Array *CmtDataW); - void ViewComment(); - void ViewFileComment(); - void SetLatestTime(RarTime *NewTime); - void SeekToNext(); - bool CheckAccess(); - bool IsArcDir(); - bool IsArcLabel(); - void ConvertAttributes(); - int GetRecoverySize(bool Required); - void VolSubtractHeaderSize(int SubSize); - void AddSubData(byte *SrcData,int DataSize,File *SrcFile,char *Name,bool AllowSplit); - bool ReadSubData(Array *UnpData,File *DestFile); - int GetHeaderType() {return(CurHeaderType);}; - int ReadCommentData(Array *CmtData,Array *CmtDataW); - void WriteCommentData(byte *Data,int DataSize,bool FileComment); - RAROptions* GetRAROptions() {return(Cmd);} - void SetSilentOpen(bool Mode) {SilentOpen=Mode;} - - BaseBlock ShortBlock; - MainHeader NewMhd; - FileHeader NewLhd; - EndArcHeader EndArcHead; - SubBlockHeader SubBlockHead; - FileHeader SubHead; - CommentHeader CommHead; - ProtectHeader ProtectHead; - AVHeader AVHead; - SignHeader SignHead; - UnixOwnersHeader UOHead; - MacFInfoHeader MACHead; - EAHeader EAHead; - StreamHeader StreamHead; - - Int64 CurBlockPos; - Int64 NextBlockPos; - - bool OldFormat; - bool Solid; - bool Volume; - bool MainComment; - bool Locked; - bool Signed; - bool NotFirstVolume; - bool Protected; - bool Encrypted; - uint SFXSize; - bool BrokenFileHeader; - - bool Splitting; - - ushort HeaderCRC; - - Int64 VolWrite; - Int64 AddingFilesSize; - uint AddingHeadersSize; - - bool NewArchive; - - char FirstVolumeName[NM]; - wchar FirstVolumeNameW[NM]; -}; - -#endif diff --git a/src/bin/unrar/arcread.cpp b/src/bin/unrar/arcread.cpp deleted file mode 100644 index 43a23db074..0000000000 --- a/src/bin/unrar/arcread.cpp +++ /dev/null @@ -1,653 +0,0 @@ -#include "rar.hpp" - -int Archive::SearchBlock(int BlockType) -{ - int Size,Count=0; - while ((Size=ReadHeader())!=0 && - (BlockType==ENDARC_HEAD || GetHeaderType()!=ENDARC_HEAD)) - { - if ((++Count & 127)==0) - Wait(); - if (GetHeaderType()==BlockType) - return(Size); - SeekToNext(); - } - return(0); -} - - -int Archive::SearchSubBlock(const char *Type) -{ - int Size; - while ((Size=ReadHeader())!=0 && GetHeaderType()!=ENDARC_HEAD) - { - if (GetHeaderType()==NEWSUB_HEAD && SubHead.CmpName(Type)) - return(Size); - SeekToNext(); - } - return(0); -} - - -int Archive::ReadHeader() -{ - CurBlockPos=Tell(); - -#ifndef SFX_MODULE - if (OldFormat) - return(ReadOldHeader()); -#endif - - RawRead Raw(this); - - bool Decrypt=Encrypted && CurBlockPos>=SFXSize+SIZEOF_MARKHEAD+SIZEOF_NEWMHD; - - if (Decrypt) - { -#if defined(SHELL_EXT) || defined(NOCRYPT) - return(0); -#else - if (Read(HeadersSalt,SALT_SIZE)!=SALT_SIZE) - return(0); - if (*Cmd->Password==0) -#ifdef RARDLL - if (Cmd->Callback==NULL || - Cmd->Callback(UCM_NEEDPASSWORD,Cmd->UserData,(LONG)Cmd->Password,sizeof(Cmd->Password))==-1) - { - Close(); - ErrHandler.Exit(USER_BREAK); - } - -#else - if (!GetPassword(PASSWORD_ARCHIVE,FileName,Cmd->Password,sizeof(Cmd->Password))) - { - Close(); - ErrHandler.Exit(USER_BREAK); - } -#endif - HeadersCrypt.SetCryptKeys(Cmd->Password,HeadersSalt,false,false,NewMhd.EncryptVer>=36); - Raw.SetCrypt(&HeadersCrypt); -#endif - } - - Raw.Read(SIZEOF_SHORTBLOCKHEAD); - if (Raw.Size()==0) - { - Int64 ArcSize=FileLength(); - if (CurBlockPos>ArcSize || NextBlockPos>ArcSize) - { - #ifndef SHELL_EXT - Log(FileName,St(MLogUnexpEOF)); - #endif - ErrHandler.SetErrorCode(WARNING); - } - return(0); - } - - Raw.Get(ShortBlock.HeadCRC); - byte HeadType; - Raw.Get(HeadType); - ShortBlock.HeadType=(HEADER_TYPE)HeadType; - Raw.Get(ShortBlock.Flags); - Raw.Get(ShortBlock.HeadSize); - if (ShortBlock.HeadSizePackSize); - Raw.Get(hd->UnpSize); - Raw.Get(hd->HostOS); - Raw.Get(hd->FileCRC); - Raw.Get(hd->FileTime); - Raw.Get(hd->UnpVer); - Raw.Get(hd->Method); - Raw.Get(hd->NameSize); - Raw.Get(hd->FileAttr); - if (hd->Flags & LHD_LARGE) - { - Raw.Get(hd->HighPackSize); - Raw.Get(hd->HighUnpSize); - } - else - { - hd->HighPackSize=hd->HighUnpSize=0; - if (hd->UnpSize==0xffffffff) - { - hd->UnpSize=int64to32(INT64MAX); - hd->HighUnpSize=int64to32(INT64MAX>>32); - } - } - hd->FullPackSize=int32to64(hd->HighPackSize,hd->PackSize); - hd->FullUnpSize=int32to64(hd->HighUnpSize,hd->UnpSize); - - char FileName[NM*4]; - int NameSize=Min(hd->NameSize,sizeof(FileName)-1); - Raw.Get((byte *)FileName,NameSize); - FileName[NameSize]=0; - - strncpyz(hd->FileName,FileName,ASIZE(hd->FileName)); - - if (hd->HeadType==NEWSUB_HEAD) - { - int DataSize=hd->HeadSize-hd->NameSize-SIZEOF_NEWLHD; - if (hd->Flags & LHD_SALT) - DataSize-=SALT_SIZE; - if (DataSize>0) - { - hd->SubData.Alloc(DataSize); - Raw.Get(&hd->SubData[0],DataSize); - if (hd->CmpName(SUBHEAD_TYPE_RR)) - { - byte *D=&hd->SubData[8]; - RecoverySectors=D[0]+((uint)D[1]<<8)+((uint)D[2]<<16)+((uint)D[3]<<24); - } - } - } - else - if (hd->HeadType==FILE_HEAD) - { - if (hd->Flags & LHD_UNICODE) - { - EncodeFileName NameCoder; - int Length=strlen(FileName); - if (Length==hd->NameSize) - { - UtfToWide(FileName,hd->FileNameW,sizeof(hd->FileNameW)/sizeof(hd->FileNameW[0])-1); - WideToChar(hd->FileNameW,hd->FileName,sizeof(hd->FileName)/sizeof(hd->FileName[0])-1); - ExtToInt(hd->FileName,hd->FileName); - } - else - { - Length++; - NameCoder.Decode(FileName,(byte *)FileName+Length, - hd->NameSize-Length,hd->FileNameW, - sizeof(hd->FileNameW)/sizeof(hd->FileNameW[0])); - } - if (*hd->FileNameW==0) - hd->Flags &= ~LHD_UNICODE; - } - else - *hd->FileNameW=0; -#ifndef SFX_MODULE - ConvertNameCase(hd->FileName); - ConvertNameCase(hd->FileNameW); -#endif - ConvertUnknownHeader(); - } - if (hd->Flags & LHD_SALT) - Raw.Get(hd->Salt,SALT_SIZE); - hd->mtime.SetDos(hd->FileTime); - hd->ctime.Reset(); - hd->atime.Reset(); - hd->arctime.Reset(); - if (hd->Flags & LHD_EXTTIME) - { - ushort Flags; - Raw.Get(Flags); - RarTime *tbl[4]; - tbl[0]=&NewLhd.mtime; - tbl[1]=&NewLhd.ctime; - tbl[2]=&NewLhd.atime; - tbl[3]=&NewLhd.arctime; - for (int I=0;I<4;I++) - { - RarTime *CurTime=tbl[I]; - uint rmode=Flags>>(3-I)*4; - if ((rmode & 8)==0) - continue; - if (I!=0) - { - uint DosTime; - Raw.Get(DosTime); - CurTime->SetDos(DosTime); - } - RarLocalTime rlt; - CurTime->GetLocal(&rlt); - if (rmode & 4) - rlt.Second++; - rlt.Reminder=0; - int count=rmode&3; - for (int J=0;JSetLocal(&rlt); - } - } - NextBlockPos+=hd->FullPackSize; - bool CRCProcessedOnly=(hd->Flags & LHD_COMMENT)!=0; - HeaderCRC=~Raw.GetCRC(CRCProcessedOnly)&0xffff; - if (hd->HeadCRC!=HeaderCRC) - { - if (hd->HeadType==NEWSUB_HEAD) - strcat(hd->FileName,"- ???"); - BrokenFileHeader=true; - ErrHandler.SetErrorCode(WARNING); -#ifndef SHELL_EXT - Log(Archive::FileName,St(MLogFileHead),IntNameToExt(hd->FileName)); - Alarm(); -#endif - } - } - break; -#ifndef SFX_MODULE - case COMM_HEAD: - *(BaseBlock *)&CommHead=ShortBlock; - Raw.Get(CommHead.UnpSize); - Raw.Get(CommHead.UnpVer); - Raw.Get(CommHead.Method); - Raw.Get(CommHead.CommCRC); - break; - case SIGN_HEAD: - *(BaseBlock *)&SignHead=ShortBlock; - Raw.Get(SignHead.CreationTime); - Raw.Get(SignHead.ArcNameSize); - Raw.Get(SignHead.UserNameSize); - break; - case AV_HEAD: - *(BaseBlock *)&AVHead=ShortBlock; - Raw.Get(AVHead.UnpVer); - Raw.Get(AVHead.Method); - Raw.Get(AVHead.AVVer); - Raw.Get(AVHead.AVInfoCRC); - break; - case PROTECT_HEAD: - *(BaseBlock *)&ProtectHead=ShortBlock; - Raw.Get(ProtectHead.DataSize); - Raw.Get(ProtectHead.Version); - Raw.Get(ProtectHead.RecSectors); - Raw.Get(ProtectHead.TotalBlocks); - Raw.Get(ProtectHead.Mark,8); - NextBlockPos+=ProtectHead.DataSize; - RecoverySectors=ProtectHead.RecSectors; - break; - case SUB_HEAD: - *(BaseBlock *)&SubBlockHead=ShortBlock; - Raw.Get(SubBlockHead.DataSize); - NextBlockPos+=SubBlockHead.DataSize; - Raw.Get(SubBlockHead.SubType); - Raw.Get(SubBlockHead.Level); - switch(SubBlockHead.SubType) - { - case UO_HEAD: - *(SubBlockHeader *)&UOHead=SubBlockHead; - Raw.Get(UOHead.OwnerNameSize); - Raw.Get(UOHead.GroupNameSize); - if (UOHead.OwnerNameSize>NM-1) - UOHead.OwnerNameSize=NM-1; - if (UOHead.GroupNameSize>NM-1) - UOHead.GroupNameSize=NM-1; - Raw.Get((byte *)UOHead.OwnerName,UOHead.OwnerNameSize); - Raw.Get((byte *)UOHead.GroupName,UOHead.GroupNameSize); - UOHead.OwnerName[UOHead.OwnerNameSize]=0; - UOHead.GroupName[UOHead.GroupNameSize]=0; - break; - case MAC_HEAD: - *(SubBlockHeader *)&MACHead=SubBlockHead; - Raw.Get(MACHead.fileType); - Raw.Get(MACHead.fileCreator); - break; - case EA_HEAD: - case BEEA_HEAD: - case NTACL_HEAD: - *(SubBlockHeader *)&EAHead=SubBlockHead; - Raw.Get(EAHead.UnpSize); - Raw.Get(EAHead.UnpVer); - Raw.Get(EAHead.Method); - Raw.Get(EAHead.EACRC); - break; - case STREAM_HEAD: - *(SubBlockHeader *)&StreamHead=SubBlockHead; - Raw.Get(StreamHead.UnpSize); - Raw.Get(StreamHead.UnpVer); - Raw.Get(StreamHead.Method); - Raw.Get(StreamHead.StreamCRC); - Raw.Get(StreamHead.StreamNameSize); - if (StreamHead.StreamNameSize>NM-1) - StreamHead.StreamNameSize=NM-1; - Raw.Get((byte *)StreamHead.StreamName,StreamHead.StreamNameSize); - StreamHead.StreamName[StreamHead.StreamNameSize]=0; - break; - } - break; -#endif - default: - if (ShortBlock.Flags & LONG_BLOCK) - { - uint DataSize; - Raw.Get(DataSize); - NextBlockPos+=DataSize; - } - break; - } - HeaderCRC=~Raw.GetCRC(false)&0xffff; - CurHeaderType=ShortBlock.HeadType; - if (Decrypt) - { - NextBlockPos+=Raw.PaddedSize()+SALT_SIZE; - - if (ShortBlock.HeadCRC!=HeaderCRC) - { - bool Recovered=false; - if (ShortBlock.HeadType==ENDARC_HEAD && (EndArcHead.Flags & EARC_REVSPACE)!=0) - { - SaveFilePos SavePos(*this); - Int64 Length=Tell(); - Seek(Length-7,SEEK_SET); - Recovered=true; - for (int J=0;J<7;J++) - if (GetByte()!=0) - Recovered=false; - } - if (!Recovered) - { -#ifndef SILENT - Log(FileName,St(MEncrBadCRC),FileName); -#endif - Close(); - - BrokenFileHeader=true; - ErrHandler.SetErrorCode(CRC_ERROR); - return(0); -// ErrHandler.Exit(CRC_ERROR); - } - } - } - - if (NextBlockPos<=CurBlockPos) - { -#ifndef SHELL_EXT - Log(FileName,St(MLogFileHead),"???"); -#endif - BrokenFileHeader=true; - ErrHandler.SetErrorCode(CRC_ERROR); - return(0); - } - return(Raw.Size()); -} - - -#ifndef SFX_MODULE -int Archive::ReadOldHeader() -{ - RawRead Raw(this); - if (CurBlockPos<=SFXSize) - { - Raw.Read(SIZEOF_OLDMHD); - Raw.Get(OldMhd.Mark,4); - Raw.Get(OldMhd.HeadSize); - Raw.Get(OldMhd.Flags); - NextBlockPos=CurBlockPos+OldMhd.HeadSize; - CurHeaderType=MAIN_HEAD; - } - else - { - OldFileHeader OldLhd; - Raw.Read(SIZEOF_OLDLHD); - NewLhd.HeadType=FILE_HEAD; - Raw.Get(NewLhd.PackSize); - Raw.Get(NewLhd.UnpSize); - Raw.Get(OldLhd.FileCRC); - Raw.Get(NewLhd.HeadSize); - Raw.Get(NewLhd.FileTime); - Raw.Get(OldLhd.FileAttr); - Raw.Get(OldLhd.Flags); - Raw.Get(OldLhd.UnpVer); - Raw.Get(OldLhd.NameSize); - Raw.Get(OldLhd.Method); - - NewLhd.Flags=OldLhd.Flags|LONG_BLOCK; - NewLhd.UnpVer=(OldLhd.UnpVer==2) ? 13 : 10; - NewLhd.Method=OldLhd.Method+0x30; - NewLhd.NameSize=OldLhd.NameSize; - NewLhd.FileAttr=OldLhd.FileAttr; - NewLhd.FileCRC=OldLhd.FileCRC; - NewLhd.FullPackSize=NewLhd.PackSize; - NewLhd.FullUnpSize=NewLhd.UnpSize; - - NewLhd.mtime.SetDos(NewLhd.FileTime); - NewLhd.ctime.Reset(); - NewLhd.atime.Reset(); - NewLhd.arctime.Reset(); - - Raw.Read(OldLhd.NameSize); - Raw.Get((byte *)NewLhd.FileName,OldLhd.NameSize); - NewLhd.FileName[OldLhd.NameSize]=0; - ConvertNameCase(NewLhd.FileName); - *NewLhd.FileNameW=0; - - if (Raw.Size()!=0) - NextBlockPos=CurBlockPos+NewLhd.HeadSize+NewLhd.PackSize; - CurHeaderType=FILE_HEAD; - } - return(NextBlockPos>CurBlockPos ? Raw.Size():0); -} -#endif - - -void Archive::ConvertNameCase(char *Name) -{ - if (Cmd->ConvertNames==NAMES_UPPERCASE) - { - IntToExt(Name,Name); - strupper(Name); - ExtToInt(Name,Name); - } - if (Cmd->ConvertNames==NAMES_LOWERCASE) - { - IntToExt(Name,Name); - strlower(Name); - ExtToInt(Name,Name); - } -} - - -#ifndef SFX_MODULE -void Archive::ConvertNameCase(wchar *Name) -{ - if (Cmd->ConvertNames==NAMES_UPPERCASE) - strupperw(Name); - if (Cmd->ConvertNames==NAMES_LOWERCASE) - strlowerw(Name); -} -#endif - - -bool Archive::IsArcDir() -{ - return((NewLhd.Flags & LHD_WINDOWMASK)==LHD_DIRECTORY); -} - - -bool Archive::IsArcLabel() -{ - return(NewLhd.HostOS<=HOST_WIN32 && (NewLhd.FileAttr & 8)); -} - - -void Archive::ConvertAttributes() -{ -#if defined(_WIN_32) || defined(_EMX) - switch(NewLhd.HostOS) - { - case HOST_MSDOS: - case HOST_OS2: - case HOST_WIN32: - break; - case HOST_UNIX: - case HOST_BEOS: - if ((NewLhd.Flags & LHD_WINDOWMASK)==LHD_DIRECTORY) - NewLhd.FileAttr=0x10; - else - NewLhd.FileAttr=0x20; - break; - default: - if ((NewLhd.Flags & LHD_WINDOWMASK)==LHD_DIRECTORY) - NewLhd.FileAttr=0x10; - else - NewLhd.FileAttr=0x20; - break; - } -#endif -#ifdef _UNIX - static mode_t mask = (mode_t) -1; - - if (mask == (mode_t) -1) - { - mask = umask(022); - umask(mask); - } - switch(NewLhd.HostOS) - { - case HOST_MSDOS: - case HOST_OS2: - case HOST_WIN32: - if (NewLhd.FileAttr & 0x10) - NewLhd.FileAttr=0x41ff & ~mask; - else - if (NewLhd.FileAttr & 1) - NewLhd.FileAttr=0x8124 & ~mask; - else - NewLhd.FileAttr=0x81b6 & ~mask; - break; - case HOST_UNIX: - case HOST_BEOS: - break; - default: - if ((NewLhd.Flags & LHD_WINDOWMASK)==LHD_DIRECTORY) - NewLhd.FileAttr=0x41ff & ~mask; - else - NewLhd.FileAttr=0x81b6 & ~mask; - break; - } -#endif -} - - -void Archive::ConvertUnknownHeader() -{ - if (NewLhd.UnpVer<20 && (NewLhd.FileAttr & 0x10)) - NewLhd.Flags|=LHD_DIRECTORY; - if (NewLhd.HostOS>=HOST_MAX) - { - if ((NewLhd.Flags & LHD_WINDOWMASK)==LHD_DIRECTORY) - NewLhd.FileAttr=0x10; - else - NewLhd.FileAttr=0x20; - } - for (char *s=NewLhd.FileName;*s!=0;s=charnext(s)) - { - if (*s=='/' || *s=='\\') - *s=CPATHDIVIDER; -#if defined(_APPLE) && !defined(UNICODE_SUPPORTED) - if ((byte)*s<32 || (byte)*s>127) - *s='_'; -#endif - } - for (wchar *s=NewLhd.FileNameW;*s!=0;s++) - if (*s=='/' || *s=='\\') - *s=CPATHDIVIDER; -} - - -#ifndef SHELL_EXT -bool Archive::ReadSubData(Array *UnpData,File *DestFile) -{ - if (HeaderCRC!=SubHead.HeadCRC) - { -#ifndef SHELL_EXT - Log(FileName,St(MSubHeadCorrupt)); -#endif - ErrHandler.SetErrorCode(CRC_ERROR); - return(false); - } - if (SubHead.Method<0x30 || SubHead.Method>0x35 || SubHead.UnpVer>/*PACK_VER*/36) - { -#ifndef SHELL_EXT - Log(FileName,St(MSubHeadUnknown)); -#endif - return(false); - } - - if (SubHead.PackSize==0 && (SubHead.Flags & LHD_SPLIT_AFTER)==0) - return(true); - - SubDataIO.Init(); - Unpack Unpack(&SubDataIO); - Unpack.Init(); - - if (DestFile==NULL) - { - UnpData->Alloc(SubHead.UnpSize); - SubDataIO.SetUnpackToMemory(&(*UnpData)[0],SubHead.UnpSize); - } - if (SubHead.Flags & LHD_PASSWORD) - if (*Cmd->Password) - SubDataIO.SetEncryption(SubHead.UnpVer,Cmd->Password, - (SubHead.Flags & LHD_SALT) ? SubHead.Salt:NULL,false, - SubHead.UnpVer>=36); - else - return(false); - SubDataIO.SetPackedSizeToRead(SubHead.PackSize); - SubDataIO.EnableShowProgress(false); - SubDataIO.SetFiles(this,DestFile); - SubDataIO.UnpVolume=(SubHead.Flags & LHD_SPLIT_AFTER); - SubDataIO.SetSubHeader(&SubHead,NULL); - Unpack.SetDestSize(SubHead.UnpSize); - if (SubHead.Method==0x30) - CmdExtract::UnstoreFile(SubDataIO,SubHead.UnpSize); - else - Unpack.DoUnpack(SubHead.UnpVer,false); - - if (SubHead.FileCRC!=~SubDataIO.UnpFileCRC) - { -#ifndef SHELL_EXT - Log(FileName,St(MSubHeadDataCRC),SubHead.FileName); -#endif - ErrHandler.SetErrorCode(CRC_ERROR); - if (UnpData!=NULL) - UnpData->Reset(); - return(false); - } - return(true); -} -#endif diff --git a/src/bin/unrar/array.hpp b/src/bin/unrar/array.hpp deleted file mode 100644 index 1130bfb8ae..0000000000 --- a/src/bin/unrar/array.hpp +++ /dev/null @@ -1,122 +0,0 @@ -#ifndef _RAR_ARRAY_ -#define _RAR_ARRAY_ - -extern ErrorHandler ErrHandler; - -template class Array -{ - private: - T *Buffer; - int BufSize; - int AllocSize; - public: - Array(); - Array(int Size); - ~Array(); - inline void CleanData(); - inline T& operator [](int Item); - inline int Size(); - void Add(int Items); - void Alloc(int Items); - void Reset(); - void operator = (Array &Src); - void Push(T Item); - T* Addr() {return(Buffer);} -}; - -template void Array::CleanData() -{ - Buffer=NULL; - BufSize=0; - AllocSize=0; -} - - -template Array::Array() -{ - CleanData(); -} - - -template Array::Array(int Size) -{ - Buffer=(T *)rarmalloc(sizeof(T)*Size); - if (Buffer==NULL && Size!=0) - ErrHandler.MemoryError(); - - AllocSize=BufSize=Size; -} - - -template Array::~Array() -{ - if (Buffer!=NULL) - rarfree(Buffer); -} - - -template inline T& Array::operator [](int Item) -{ - return(Buffer[Item]); -} - - -template inline int Array::Size() -{ - return(BufSize); -} - - -template void Array::Add(int Items) -{ - BufSize+=Items; - if (BufSize>AllocSize) - { - int Suggested=AllocSize+AllocSize/4+32; - int NewSize=Max(BufSize,Suggested); - - Buffer=(T *)rarrealloc(Buffer,NewSize*sizeof(T)); - if (Buffer==NULL) - ErrHandler.MemoryError(); - AllocSize=NewSize; - } -} - - -template void Array::Alloc(int Items) -{ - if (Items>AllocSize) - Add(Items-BufSize); - else - BufSize=Items; -} - - -template void Array::Reset() -{ - if (Buffer!=NULL) - { - rarfree(Buffer); - Buffer=NULL; - } - BufSize=0; - AllocSize=0; -} - - -template void Array::operator =(Array &Src) -{ - Reset(); - Alloc(Src.BufSize); - if (Src.BufSize!=0) - memcpy((void *)Buffer,(void *)Src.Buffer,Src.BufSize*sizeof(T)); -} - - -template void Array::Push(T Item) -{ - Add(1); - (*this)[Size()-1]=Item; -} - -#endif diff --git a/src/bin/unrar/beosea.cpp b/src/bin/unrar/beosea.cpp deleted file mode 100644 index 86eb7d400c..0000000000 --- a/src/bin/unrar/beosea.cpp +++ /dev/null @@ -1,113 +0,0 @@ - - -void ExtractBeEA(Archive &Arc,char *FileName) -{ - if (Arc.HeaderCRC!=Arc.EAHead.HeadCRC) - { - Log(Arc.FileName,St(MEABroken),FileName); - ErrHandler.SetErrorCode(CRC_ERROR); - return; - } - if (Arc.EAHead.Method<0x31 || Arc.EAHead.Method>0x35 || Arc.EAHead.UnpVer>PACK_VER) - { - Log(Arc.FileName,St(MEAUnknHeader),FileName); - return; - } - - ComprDataIO DataIO; - Unpack Unpack(&DataIO); - Unpack.Init(); - - Array UnpData(Arc.EAHead.UnpSize); - DataIO.SetUnpackToMemory(&UnpData[0],Arc.EAHead.UnpSize); - DataIO.SetPackedSizeToRead(Arc.EAHead.DataSize); - DataIO.EnableShowProgress(false); - DataIO.SetFiles(&Arc,NULL); - Unpack.SetDestSize(Arc.EAHead.UnpSize); - Unpack.DoUnpack(Arc.EAHead.UnpVer,false); - - if (Arc.EAHead.EACRC!=~DataIO.UnpFileCRC) - { - Log(Arc.FileName,St(MEABroken),FileName); - ErrHandler.SetErrorCode(CRC_ERROR); - return; - } - int fd = open(FileName,O_WRONLY); - if (fd==-1) - { - Log(Arc.FileName,St(MCannotSetEA),FileName); - ErrHandler.SetErrorCode(WARNING); - return; - } - - int AttrPos=0; - while (AttrPos=sizeof(Name)) - { - Log(Arc.FileName,St(MCannotSetEA),FileName); - ErrHandler.SetErrorCode(WARNING); - break; - } - memcpy(Name,CurItem+10,NameSize); - Name[NameSize]=0; - if (fs_write_attr(fd,Name,Type,0,CurItem+10+NameSize,Size)==-1) - { - Log(Arc.FileName,St(MCannotSetEA),FileName); - ErrHandler.SetErrorCode(WARNING); - break; - } - AttrPos+=10+NameSize+Size; - } - close(fd); - mprintf(St(MShowEA)); -} - - -void ExtractBeEANew(Archive &Arc,char *FileName) -{ - Array SubData; - if (!Arc.ReadSubData(&SubData,NULL)) - return; - - int fd = open(FileName,O_WRONLY); - if (fd==-1) - { - Log(Arc.FileName,St(MCannotSetEA),FileName); - ErrHandler.SetErrorCode(WARNING); - return; - } - - int AttrPos=0; - while (AttrPos=sizeof(Name)) - { - Log(Arc.FileName,St(MCannotSetEA),FileName); - ErrHandler.SetErrorCode(WARNING); - break; - } - memcpy(Name,CurItem+10,NameSize); - Name[NameSize]=0; - if (fs_write_attr(fd,Name,Type,0,CurItem+10+NameSize,Size)==-1) - { - Log(Arc.FileName,St(MCannotSetEA),FileName); - ErrHandler.SetErrorCode(WARNING); - break; - } - AttrPos+=10+NameSize+Size; - } - close(fd); - mprintf(St(MShowEA)); -} - diff --git a/src/bin/unrar/cmddata.cpp b/src/bin/unrar/cmddata.cpp deleted file mode 100644 index 41f3dd7e39..0000000000 --- a/src/bin/unrar/cmddata.cpp +++ /dev/null @@ -1,1287 +0,0 @@ -#include "rar.hpp" - -CommandData::CommandData() -{ - FileArgs=ExclArgs=InclArgs=StoreArgs=ArcNames=NULL; - Init(); -} - - -CommandData::~CommandData() -{ - Close(); -} - - -void CommandData::Init() -{ - Close(); - - *Command=0; - *ArcName=0; - *ArcNameW=0; - FileLists=false; - NoMoreSwitches=false; - TimeConverted=false; - - FileArgs=new StringList; - ExclArgs=new StringList; - InclArgs=new StringList; - StoreArgs=new StringList; - ArcNames=new StringList; -} - - -void CommandData::Close() -{ - delete FileArgs; - delete ExclArgs; - delete InclArgs; - delete StoreArgs; - delete ArcNames; - FileArgs=ExclArgs=InclArgs=StoreArgs=ArcNames=NULL; - NextVolSizes.Reset(); -} - - -#if !defined(SFX_MODULE) -void CommandData::ParseArg(char *Arg,wchar *ArgW) -{ - if (IsSwitch(*Arg) && !NoMoreSwitches) - if (Arg[1]=='-') - NoMoreSwitches=true; - else - ProcessSwitch(&Arg[1]); - else - if (*Command==0) - { - strncpyz(Command,Arg,ASIZE(Command)); - if (ArgW!=NULL) - strncpyw(CommandW,ArgW,sizeof(CommandW)/sizeof(CommandW[0])); - if (etoupper(*Command)=='S') - { - const char *SFXName=Command[1] ? Command+1:DefSFXName; - if (PointToName(SFXName)!=SFXName || FileExist(SFXName)) - strcpy(SFXModule,SFXName); - else - GetConfigName(SFXName,SFXModule,true); - } -#ifndef GUI - *Command=etoupper(*Command); - if (*Command!='I' && *Command!='S') - strupper(Command); -#endif - } - else - if (*ArcName==0) - { - strncpyz(ArcName,Arg,ASIZE(ArcName)); - if (ArgW!=NULL) - strncpyzw(ArcNameW,ArgW,ASIZE(ArcNameW)); - } - else - { - int Length=strlen(Arg); - char EndChar=Arg[Length-1]; - char CmdChar=etoupper(*Command); - bool Add=strchr("AFUM",CmdChar)!=NULL; - bool Extract=CmdChar=='X' || CmdChar=='E'; - if ((IsDriveDiv(EndChar) || IsPathDiv(EndChar)) && !Add) - { - strncpyz(ExtrPath,Arg,ASIZE(ExtrPath)); - if (ArgW!=NULL) - strncpyzw(ExtrPathW,ArgW,ASIZE(ExtrPathW)); - } - else - if ((Add || CmdChar=='T') && *Arg!='@') - FileArgs->AddString(Arg); - else - { - struct FindData FileData; - bool Found=FindFile::FastFind(Arg,NULL,&FileData); - if (!Found && *Arg=='@' && !IsWildcard(Arg)) - { - FileLists=true; - - RAR_CHARSET Charset=FilelistCharset; - -#if defined(_WIN_32) && !defined(GUI) - // for compatibility reasons we use OEM encoding - // in Win32 console version by default - - if (Charset==RCH_DEFAULT) - Charset=RCH_OEM; -#endif - - ReadTextFile(Arg+1,FileArgs,false,true,Charset,true,true); - } - else - if (Found && FileData.IsDir && Extract && *ExtrPath==0) - { - strcpy(ExtrPath,Arg); - AddEndSlash(ExtrPath); - } - else - FileArgs->AddString(Arg); - } - } -} -#endif - - -void CommandData::ParseDone() -{ - if (FileArgs->ItemsCount()==0 && !FileLists) - FileArgs->AddString(MASKALL); - char CmdChar=etoupper(*Command); - bool Extract=CmdChar=='X' || CmdChar=='E'; - if (Test && Extract) - Test=false; - BareOutput=(CmdChar=='L' || CmdChar=='V') && Command[1]=='B'; -} - - -#if !defined(SFX_MODULE) && !defined(_WIN_CE) -void CommandData::ParseEnvVar() -{ - char *EnvStr=getenv("RAR"); - if (EnvStr!=NULL) - ProcessSwitchesString(EnvStr); -} -#endif - - - -// return 'false' if -cfg- is present and preprocess switches -// which must be processed before the rest of command line - -#ifndef SFX_MODULE -bool CommandData::IsConfigEnabled(int argc,char *argv[]) -{ - bool ConfigEnabled=true; - for (int I=1;I='0' && Switch[2]<='4'; - if (CommonMode) - Mode=(EXTTIME_MODE)(Switch[2]-'0'); - if (Switch[2]=='-') - Mode=EXTTIME_NONE; - if (CommonMode || Switch[2]=='-' || Switch[2]=='+' || Switch[2]==0) - xmtime=xctime=xatime=Mode; - else - { - if (Switch[3]>='0' && Switch[3]<='4') - Mode=(EXTTIME_MODE)(Switch[3]-'0'); - if (Switch[3]=='-') - Mode=EXTTIME_NONE; - switch(etoupper(Switch[2])) - { - case 'M': - xmtime=Mode; - break; - case 'C': - xctime=Mode; - break; - case 'A': - xatime=Mode; - break; - case 'R': - xarctime=Mode; - break; - } - } - } - break; - case '-': - Test=false; - break; - case 0: - Test=true; - break; - default: - BadSwitch(Switch); - break; - } - break; - case 'A': - switch(etoupper(Switch[1])) - { - case 'C': - ClearArc=true; - break; - case 'D': - AppendArcNameToPath=true; - break; - case 'G': - if (Switch[2]=='-' && Switch[3]==0) - GenerateArcName=0; - else - { - GenerateArcName=true; - strncpyz(GenerateMask,Switch+2,ASIZE(GenerateMask)); - } - break; - case 'N': //reserved for archive name - break; - case 'O': - AddArcOnly=true; - break; - case 'P': - strcpy(ArcPath,Switch+2); - break; - case 'S': - SyncFiles=true; - break; - default: - BadSwitch(Switch); - break; - } - break; - case 'D': - if (Switch[2]==0) - switch(etoupper(Switch[1])) - { - case 'S': - DisableSortSolid=true; - break; - case 'H': - OpenShared=true; - break; - case 'F': - DeleteFiles=true; - break; - } - break; - case 'O': - switch(etoupper(Switch[1])) - { - case '+': - Overwrite=OVERWRITE_ALL; - break; - case '-': - Overwrite=OVERWRITE_NONE; - break; - case 'R': - Overwrite=OVERWRITE_AUTORENAME; - break; - case 'W': - ProcessOwners=true; - break; -#ifdef SAVE_LINKS - case 'L': - SaveLinks=true; - break; -#endif -#ifdef _WIN_32 - case 'S': - SaveStreams=true; - break; - case 'C': - SetCompressedAttr=true; - break; -#endif - default : - BadSwitch(Switch); - break; - } - break; - case 'R': - switch(etoupper(Switch[1])) - { - case 0: - Recurse=RECURSE_ALWAYS; - break; - case '-': - Recurse=0; - break; - case '0': - Recurse=RECURSE_WILDCARDS; - break; -#ifndef _WIN_CE - case 'I': - { - Priority=atoi(Switch+2); - char *ChPtr=strchr(Switch+2,':'); - if (ChPtr!=NULL) - { - SleepTime=atoi(ChPtr+1); - InitSystemOptions(SleepTime); - } - SetPriority(Priority); - } - break; -#endif - } - break; - case 'Y': - AllYes=true; - break; - case 'N': - case 'X': - if (Switch[1]!=0) - { - StringList *Args=etoupper(Switch[0])=='N' ? InclArgs:ExclArgs; - if (Switch[1]=='@' && !IsWildcard(Switch)) - { - RAR_CHARSET Charset=FilelistCharset; - -#if defined(_WIN_32) && !defined(GUI) - // for compatibility reasons we use OEM encoding - // in Win32 console version by default - - if (Charset==RCH_DEFAULT) - Charset=RCH_OEM; -#endif - - ReadTextFile(Switch+2,Args,false,true,Charset,true,true); - } - else - Args->AddString(Switch+1); - } - break; - case 'E': - switch(etoupper(Switch[1])) - { - case 'P': - switch(Switch[2]) - { - case 0: - ExclPath=EXCL_SKIPWHOLEPATH; - break; - case '1': - ExclPath=EXCL_BASEPATH; - break; - case '2': - ExclPath=EXCL_SAVEFULLPATH; - break; - case '3': - ExclPath=EXCL_ABSPATH; - break; - } - break; - case 'D': - ExclEmptyDir=true; - break; - case 'E': - ProcessEA=false; - break; - case 'N': - NoEndBlock=true; - break; - default: - if (Switch[1]=='+') - { - InclFileAttr=GetExclAttr(&Switch[2]); - InclAttrSet=true; - } - else - ExclFileAttr=GetExclAttr(&Switch[1]); - break; - } - break; - case 'P': - if (Switch[1]==0) - { - GetPassword(PASSWORD_GLOBAL,NULL,Password,sizeof(Password)); - eprintf("\n"); - } - else - strncpyz(Password,Switch+1,ASIZE(Password)); - break; - case 'H': - if (etoupper(Switch[1])=='P') - { - EncryptHeaders=true; - if (Switch[2]!=0) - strncpyz(Password,Switch+2,ASIZE(Password)); - else - if (*Password==0) - { - GetPassword(PASSWORD_GLOBAL,NULL,Password,sizeof(Password)); - eprintf("\n"); - } - } - break; - case 'Z': - strncpyz(CommentFile,Switch[1]!=0 ? Switch+1:"stdin",ASIZE(CommentFile)); - break; - case 'M': - switch(etoupper(Switch[1])) - { - case 'C': - { - char *Str=Switch+2; - if (*Str=='-') - for (int I=0;IAddString(Mask); - if (End==NULL) - break; - Names=End+1; - } - } - break; -#ifdef PACK_SMP - case 'T': - Threads=atoi(Switch+2); - if (Threads>MaxSearchThreads) - BadSwitch(Switch); - else - { - } - break; -#endif - default: - Method=Switch[1]-'0'; - if (Method>5 || Method<0) - BadSwitch(Switch); - break; - } - break; - case 'V': - switch(etoupper(Switch[1])) - { -#ifdef _WIN_32 - case 'D': - EraseDisk=true; - break; -#endif - case 'N': - OldNumbering=true; - break; - case 'P': - VolumePause=true; - break; - case 'E': - if (etoupper(Switch[2])=='R') - VersionControl=atoi(Switch+3)+1; - break; - case '-': - VolSize=0; - break; - default: - { - Int64 NewVolSize=atoil(&Switch[1]); - - if (NewVolSize==0) - NewVolSize=INT64ERR; - else - switch (Switch[strlen(Switch)-1]) - { - case 'f': - case 'F': - switch(int64to32(NewVolSize)) - { - case 360: - NewVolSize=362496; - break; - case 720: - NewVolSize=730112; - break; - case 1200: - NewVolSize=1213952; - break; - case 1440: - NewVolSize=1457664; - break; - case 2880: - NewVolSize=2915328; - break; - } - break; - case 'k': - NewVolSize*=1024; - break; - case 'm': - NewVolSize*=1024*1024; - break; - case 'M': - NewVolSize*=1000*1000; - break; - case 'g': - NewVolSize*=1024*1024; - NewVolSize*=1024; - break; - case 'G': - NewVolSize*=1000*1000; - NewVolSize*=1000; - break; - case 'b': - case 'B': - break; - default: - NewVolSize*=1000; - break; - } - if (VolSize==0) - VolSize=NewVolSize; - else - NextVolSizes.Push(NewVolSize); - } - break; - } - break; - case 'F': - if (Switch[1]==0) - FreshFiles=true; - else - BadSwitch(Switch); - break; - case 'U': - if (Switch[1]==0) - UpdateFiles=true; - else - BadSwitch(Switch); - break; - case 'W': - strncpyz(TempPath,&Switch[1],ASIZE(TempPath)); - AddEndSlash(TempPath); - break; - case 'S': - if (strnicomp(Switch,"SFX",3)==0) - { - const char *SFXName=Switch[3] ? Switch+3:DefSFXName; - if (PointToName(SFXName)!=SFXName || FileExist(SFXName)) - strcpy(SFXModule,SFXName); - else - GetConfigName(SFXName,SFXModule,true); - } - if (isdigit(Switch[1])) - { - Solid|=SOLID_COUNT; - SolidCount=atoi(&Switch[1]); - } - else - switch(etoupper(Switch[1])) - { - case 0: - Solid|=SOLID_NORMAL; - break; - case '-': - Solid=SOLID_NONE; - break; - case 'E': - Solid|=SOLID_FILEEXT; - break; - case 'V': - Solid|=Switch[2]=='-' ? SOLID_VOLUME_DEPENDENT:SOLID_VOLUME_INDEPENDENT; - break; - case 'D': - Solid|=SOLID_VOLUME_DEPENDENT; - break; - case 'L': - if (isdigit(Switch[2])) - FileSizeLess=atoil(Switch+2); - break; - case 'M': - if (isdigit(Switch[2])) - FileSizeMore=atoil(Switch+2); - break; - case 'C': - { - RAR_CHARSET rch; - switch(etoupper(Switch[2])) - { - case 'A': - rch=RCH_ANSI; - break; - case 'O': - rch=RCH_OEM; - break; - case 'U': - rch=RCH_UNICODE; - break; - default : - BadSwitch(Switch); - break; - }; - if (Switch[3]==0) - CommentCharset=FilelistCharset=rch; - else - for (int I=3;Switch[I]!=0;I++) - switch(etoupper(Switch[I])) - { - case 'C': - CommentCharset=rch; - break; - case 'L': - FilelistCharset=rch; - break; - default: - BadSwitch(Switch); - break; - } - } - break; - - } - break; - case 'C': - if (Switch[2]==0) - switch(etoupper(Switch[1])) - { - case '-': - DisableComment=true; - break; - case 'U': - ConvertNames=NAMES_UPPERCASE; - break; - case 'L': - ConvertNames=NAMES_LOWERCASE; - break; - } - break; - case 'K': - switch(etoupper(Switch[1])) - { - case 'B': - KeepBroken=true; - break; - case 0: - Lock=true; - break; - } - break; -#ifndef GUI - case '?' : - OutHelp(); - break; -#endif - default : - BadSwitch(Switch); - break; - } -} -#endif - - -#ifndef SFX_MODULE -void CommandData::BadSwitch(char *Switch) -{ - mprintf(St(MUnknownOption),Switch); - ErrHandler.Exit(USER_ERROR); -} -#endif - - -#ifndef GUI -void CommandData::OutTitle() -{ - if (BareOutput || DisableCopyright) - return; -#if defined(__GNUC__) && defined(SFX_MODULE) - mprintf(St(MCopyrightS)); -#else -#ifndef SILENT - static bool TitleShown=false; - if (TitleShown) - return; - TitleShown=true; - char Version[50]; - int Beta=RARVER_BETA; - if (Beta!=0) - sprintf(Version,"%d.%02d %s %d",RARVER_MAJOR,RARVER_MINOR,St(MBeta),RARVER_BETA); - else - sprintf(Version,"%d.%02d",RARVER_MAJOR,RARVER_MINOR); -#ifdef UNRAR - mprintf(St(MUCopyright),Version,RARVER_YEAR); -#else -#endif -#endif -#endif -} -#endif - - -void CommandData::OutHelp() -{ -#if !defined(GUI) && !defined(SILENT) - OutTitle(); - static MSGID Help[]={ -#ifdef SFX_MODULE - MCHelpCmd,MSHelpCmdE,MSHelpCmdT,MSHelpCmdV -#elif defined(UNRAR) - MUNRARTitle1,MRARTitle2,MCHelpCmd,MCHelpCmdE,MCHelpCmdL,MCHelpCmdP, - MCHelpCmdT,MCHelpCmdV,MCHelpCmdX,MCHelpSw,MCHelpSwm,MCHelpSwAC,MCHelpSwAD, - MCHelpSwAP,MCHelpSwAVm,MCHelpSwCm,MCHelpSwCFGm,MCHelpSwCL,MCHelpSwCU, - MCHelpSwDH,MCHelpSwEP,MCHelpSwEP3,MCHelpSwF,MCHelpSwIDP,MCHelpSwIERR, - MCHelpSwINUL,MCHelpSwIOFF,MCHelpSwKB,MCHelpSwN,MCHelpSwNa,MCHelpSwNal, - MCHelpSwOp,MCHelpSwOm,MCHelpSwOC,MCHelpSwOR,MCHelpSwOW,MCHelpSwP, - MCHelpSwPm,MCHelpSwR,MCHelpSwRI,MCHelpSwSL,MCHelpSwSM,MCHelpSwTA, - MCHelpSwTB,MCHelpSwTN,MCHelpSwTO,MCHelpSwTS,MCHelpSwU,MCHelpSwVUnr, - MCHelpSwVER,MCHelpSwVP,MCHelpSwX,MCHelpSwXa,MCHelpSwXal,MCHelpSwY -#else - MRARTitle1,MRARTitle2,MCHelpCmd,MCHelpCmdA,MCHelpCmdC,MCHelpCmdCF, - MCHelpCmdCH,MCHelpCmdCW,MCHelpCmdD,MCHelpCmdE,MCHelpCmdF,MCHelpCmdI, - MCHelpCmdK,MCHelpCmdL,MCHelpCmdM,MCHelpCmdP,MCHelpCmdR,MCHelpCmdRC, - MCHelpCmdRN,MCHelpCmdRR,MCHelpCmdRV,MCHelpCmdS,MCHelpCmdT,MCHelpCmdU, - MCHelpCmdV,MCHelpCmdX,MCHelpSw,MCHelpSwm,MCHelpSwAC,MCHelpSwAD,MCHelpSwAG, - MCHelpSwAO,MCHelpSwAP,MCHelpSwAS,MCHelpSwAV,MCHelpSwAVm,MCHelpSwCm, - MCHelpSwCFGm,MCHelpSwCL,MCHelpSwCU,MCHelpSwDF,MCHelpSwDH,MCHelpSwDS, - MCHelpSwEa,MCHelpSwED,MCHelpSwEE,MCHelpSwEN,MCHelpSwEP,MCHelpSwEP1, - MCHelpSwEP2,MCHelpSwEP3,MCHelpSwF,MCHelpSwHP,MCHelpSwIDP, - MCHelpSwIEML,MCHelpSwIERR,MCHelpSwILOG,MCHelpSwINUL,MCHelpSwIOFF, - MCHelpSwISND,MCHelpSwK,MCHelpSwKB,MCHelpSwMn,MCHelpSwMC,MCHelpSwMD, - MCHelpSwMS,MCHelpSwMT,MCHelpSwN,MCHelpSwNa,MCHelpSwNal,MCHelpSwOp, - MCHelpSwOm,MCHelpSwOC,MCHelpSwOL,MCHelpSwOR,MCHelpSwOS,MCHelpSwOW, - MCHelpSwP,MCHelpSwPm,MCHelpSwR,MCHelpSwR0,MCHelpSwRI,MCHelpSwRR, - MCHelpSwRV,MCHelpSwS,MCHelpSwSm,MCHelpSwSC,MCHelpSwSFX,MCHelpSwSI, - MCHelpSwSL,MCHelpSwSM,MCHelpSwT,MCHelpSwTA,MCHelpSwTB,MCHelpSwTK, - MCHelpSwTL,MCHelpSwTN,MCHelpSwTO,MCHelpSwTS,MCHelpSwU,MCHelpSwV, - MCHelpSwVn,MCHelpSwVD,MCHelpSwVER,MCHelpSwVN,MCHelpSwVP,MCHelpSwW, - MCHelpSwX,MCHelpSwXa,MCHelpSwXal,MCHelpSwY,MCHelpSwZ -#endif - }; - - for (int I=0;IRewind(); - while ((CurName=Args->GetString())!=NULL) -#ifndef SFX_MODULE - if (CheckFullPath && IsFullPath(CurName)) - { - if (*FullName==0) - ConvertNameToFull(CheckName,FullName); - if (CmpName(CurName,FullName,MatchMode)) - return(true); - } - else -#endif - if (CmpName(ConvertPath(CurName,NULL),Name,MatchMode)) - return(true); - return(false); -} - - -bool CommandData::ExclCheck(char *CheckName,bool CheckFullPath) -{ - if (ExclCheckArgs(ExclArgs,CheckName,CheckFullPath,MATCH_WILDSUBPATH)) - return(true); - if (InclArgs->ItemsCount()==0) - return(false); - if (ExclCheckArgs(InclArgs,CheckName,false,MATCH_WILDSUBPATH)) - return(false); - return(true); -} - - - - -#ifndef SFX_MODULE -bool CommandData::TimeCheck(RarTime &ft) -{ - if (FileTimeBefore.IsSet() && ft>=FileTimeBefore) - return(true); - if (FileTimeAfter.IsSet() && ft<=FileTimeAfter) - return(true); -/* - if (FileTimeOlder!=0 || FileTimeNewer!=0) - { - if (!TimeConverted) - { - if (FileTimeOlder!=0) - FileTimeOlder=SecondsToDosTime(FileTimeOlder); - if (FileTimeNewer!=0) - FileTimeNewer=SecondsToDosTime(FileTimeNewer); - TimeConverted=true; - } - if (FileTimeOlder!=0 && ft>=FileTimeOlder) - return(true); - if (FileTimeNewer!=0 && ft<=FileTimeNewer) - return(true); - - } -*/ - return(false); -} -#endif - - -#ifndef SFX_MODULE -bool CommandData::SizeCheck(Int64 Size) -{ - if (FileSizeLess!=INT64ERR && Size>=FileSizeLess) - return(true); - if (FileSizeMore!=INT64ERR && Size<=FileSizeMore) - return(true); - return(false); -} -#endif - - -int CommandData::IsProcessFile(FileHeader &NewLhd,bool *ExactMatch,int MatchType) -{ - if (strlen(NewLhd.FileName)>=NM || strlenw(NewLhd.FileNameW)>=NM) - return(0); - if (ExclCheck(NewLhd.FileName,false)) - return(0); -#ifndef SFX_MODULE - if (TimeCheck(NewLhd.mtime)) - return(0); - if ((NewLhd.FileAttr & ExclFileAttr)!=0 || InclAttrSet && (NewLhd.FileAttr & InclFileAttr)==0) - return(0); - if ((NewLhd.Flags & LHD_WINDOWMASK)!=LHD_DIRECTORY && SizeCheck(NewLhd.FullUnpSize)) - return(0); -#endif - char *ArgName; - wchar *ArgNameW; - FileArgs->Rewind(); - for (int StringCount=1;FileArgs->GetString(&ArgName,&ArgNameW);StringCount++) - { -#ifndef SFX_MODULE - bool Unicode=(NewLhd.Flags & LHD_UNICODE) || ArgNameW!=NULL; - if (Unicode) - { - wchar NameW[NM],ArgW[NM],*NamePtr=NewLhd.FileNameW; - bool CorrectUnicode=true; - if (ArgNameW==NULL) - { - if (!CharToWide(ArgName,ArgW) || *ArgW==0) - CorrectUnicode=false; - ArgNameW=ArgW; - } - if ((NewLhd.Flags & LHD_UNICODE)==0) - { - if (!CharToWide(NewLhd.FileName,NameW) || *NameW==0) - CorrectUnicode=false; - NamePtr=NameW; - } - if (CmpName(ArgNameW,NamePtr,MatchType)) - { - if (ExactMatch!=NULL) - *ExactMatch=stricompcw(ArgNameW,NamePtr)==0; - return(StringCount); - } - if (CorrectUnicode) - continue; - } -#endif - if (CmpName(ArgName,NewLhd.FileName,MatchType)) - { - if (ExactMatch!=NULL) - *ExactMatch=stricompc(ArgName,NewLhd.FileName)==0; - return(StringCount); - } - } - return(0); -} - - -#ifndef GUI -void CommandData::ProcessCommand() -{ -#ifndef SFX_MODULE - - const char *SingleCharCommands="FUADPXETK"; - if (Command[1] && strchr(SingleCharCommands,*Command)!=NULL || *ArcName==0) - OutHelp(); - -#ifdef _UNIX - if (GetExt(ArcName)==NULL && (!FileExist(ArcName) || IsDir(GetFileAttr(ArcName)))) - strcat(ArcName,".rar"); -#else - if (GetExt(ArcName)==NULL) - strcat(ArcName,".rar"); -#endif - - if (strchr("AFUMD",*Command)==NULL) - { - StringList ArcMasks; - ArcMasks.AddString(ArcName); - ScanTree Scan(&ArcMasks,Recurse,SaveLinks,SCAN_SKIPDIRS); - FindData FindData; - while (Scan.GetNext(&FindData)==SCAN_SUCCESS) - AddArcName(FindData.Name,FindData.NameW); - } - else - AddArcName(ArcName,NULL); -#endif - - switch(Command[0]) - { - case 'P': - case 'X': - case 'E': - case 'T': - case 'I': - { - CmdExtract Extract; - Extract.DoExtract(this); - } - break; -#ifndef SILENT - case 'V': - case 'L': - ListArchive(this); - break; - default: - OutHelp(); -#endif - } - if (!BareOutput) - mprintf("\n"); -} -#endif - - -void CommandData::AddArcName(char *Name,wchar *NameW) -{ - ArcNames->AddString(Name,NameW); -} - - -bool CommandData::GetArcName(char *Name,wchar *NameW,int MaxSize) -{ - if (!ArcNames->GetString(Name,NameW,NM)) - return(false); - return(true); -} - - -bool CommandData::IsSwitch(int Ch) -{ -#if defined(_WIN_32) || defined(_EMX) - return(Ch=='-' || Ch=='/'); -#else - return(Ch=='-'); -#endif -} - - -#ifndef SFX_MODULE -uint CommandData::GetExclAttr(char *Str) -{ - if (isdigit(*Str)) - return(strtol(Str,NULL,0)); - else - { - uint Attr; - for (Attr=0;*Str;Str++) - switch(etoupper(*Str)) - { -#ifdef _UNIX - case 'D': - Attr|=S_IFDIR; - break; - case 'V': - Attr|=S_IFCHR; - break; -#elif defined(_WIN_32) || defined(_EMX) - case 'R': - Attr|=0x1; - break; - case 'H': - Attr|=0x2; - break; - case 'S': - Attr|=0x4; - break; - case 'D': - Attr|=0x10; - break; - case 'A': - Attr|=0x20; - break; -#endif - } - return(Attr); - } -} -#endif - - - - -#ifndef SFX_MODULE -bool CommandData::CheckWinSize() -{ - static int ValidSize[]={ - 0x10000,0x20000,0x40000,0x80000,0x100000,0x200000,0x400000 - }; - for (int I=0;IGetChar()); -} - - -void RangeCoder::InitDecoder(Unpack *UnpackRead) -{ - RangeCoder::UnpackRead=UnpackRead; - - low=code=0; - range=uint(-1); - for (int i=0;i < 4;i++) - code=(code << 8) | GetChar(); -} - - -#define ARI_DEC_NORMALIZE(code,low,range,read) \ -{ \ - while ((low^(low+range))GetChar(); \ - range <<= 8; \ - low <<= 8; \ - } \ -} - - -inline int RangeCoder::GetCurrentCount() -{ - return (code-low)/(range /= SubRange.scale); -} - - -inline uint RangeCoder::GetCurrentShiftCount(uint SHIFT) -{ - return (code-low)/(range >>= SHIFT); -} - - -inline void RangeCoder::Decode() -{ - low += range*SubRange.LowCount; - range *= SubRange.HighCount-SubRange.LowCount; -} diff --git a/src/bin/unrar/coder.hpp b/src/bin/unrar/coder.hpp deleted file mode 100644 index f09f911c09..0000000000 --- a/src/bin/unrar/coder.hpp +++ /dev/null @@ -1,24 +0,0 @@ -/**************************************************************************** - * Contents: 'Carryless rangecoder' by Dmitry Subbotin * - ****************************************************************************/ - -const uint TOP=1 << 24, BOT=1 << 15; - -class RangeCoder -{ - public: - void InitDecoder(Unpack *UnpackRead); - inline int GetCurrentCount(); - inline uint GetCurrentShiftCount(uint SHIFT); - inline void Decode(); - inline void PutChar(unsigned int c); - inline unsigned int GetChar(); - - uint low, code, range; - struct SUBRANGE - { - uint LowCount, HighCount, scale; - } SubRange; - - Unpack *UnpackRead; -}; diff --git a/src/bin/unrar/compress.hpp b/src/bin/unrar/compress.hpp deleted file mode 100644 index 3181e45de7..0000000000 --- a/src/bin/unrar/compress.hpp +++ /dev/null @@ -1,36 +0,0 @@ -#ifndef _RAR_COMPRESS_ -#define _RAR_COMPRESS_ - -class ComprDataIO; -class PackingFileTable; - -#define CODEBUFSIZE 0x4000 -#define MAXWINSIZE 0x400000 -#define MAXWINMASK (MAXWINSIZE-1) - -#define LOW_DIST_REP_COUNT 16 - -#define NC 299 /* alphabet = {0, 1, 2, ..., NC - 1} */ -#define DC 60 -#define LDC 17 -#define RC 28 -#define HUFF_TABLE_SIZE (NC+DC+RC+LDC) -#define BC 20 - -#define NC20 298 /* alphabet = {0, 1, 2, ..., NC - 1} */ -#define DC20 48 -#define RC20 28 -#define BC20 19 -#define MC20 257 - -enum {CODE_HUFFMAN,CODE_LZ,CODE_LZ2,CODE_REPEATLZ,CODE_CACHELZ, - CODE_STARTFILE,CODE_ENDFILE,CODE_VM,CODE_VMDATA}; - - -enum FilterType { - FILTER_NONE, FILTER_PPM /*dummy*/, FILTER_E8, FILTER_E8E9, - FILTER_UPCASETOLOW, FILTER_AUDIO, FILTER_RGB, FILTER_DELTA, - FILTER_ITANIUM, FILTER_E8E9V2 -}; - -#endif diff --git a/src/bin/unrar/consio.cpp b/src/bin/unrar/consio.cpp deleted file mode 100644 index f1f4ba0965..0000000000 --- a/src/bin/unrar/consio.cpp +++ /dev/null @@ -1,289 +0,0 @@ -#include "rar.hpp" - -#ifndef GUI -#include "log.cpp" -#endif - -#if !defined(GUI) && !defined(SILENT) -static void RawPrint(char *Msg,MESSAGE_TYPE MessageType); -#endif - -static MESSAGE_TYPE MsgStream=MSG_STDOUT; -static bool Sound=false; -const int MaxMsgSize=2*NM+2048; - -void InitConsoleOptions(MESSAGE_TYPE MsgStream,bool Sound) -{ - ::MsgStream=MsgStream; - ::Sound=Sound; -} - -#if !defined(GUI) && !defined(SILENT) -void mprintf(const char *fmt,...) -{ - if (MsgStream==MSG_NULL || MsgStream==MSG_ERRONLY) - return; - safebuf char Msg[MaxMsgSize]; - va_list argptr; - va_start(argptr,fmt); - vsprintf(Msg,fmt,argptr); - RawPrint(Msg,MsgStream); - va_end(argptr); -} -#endif - - -#if !defined(GUI) && !defined(SILENT) -void eprintf(const char *fmt,...) -{ - if (MsgStream==MSG_NULL) - return; - safebuf char Msg[MaxMsgSize]; - va_list argptr; - va_start(argptr,fmt); - vsprintf(Msg,fmt,argptr); - RawPrint(Msg,MSG_STDERR); - va_end(argptr); -} -#endif - - -#if !defined(GUI) && !defined(SILENT) -void RawPrint(char *Msg,MESSAGE_TYPE MessageType) -{ - File OutFile; - switch(MessageType) - { - case MSG_STDOUT: - OutFile.SetHandleType(FILE_HANDLESTD); - break; - case MSG_STDERR: - case MSG_ERRONLY: - OutFile.SetHandleType(FILE_HANDLEERR); - break; - default: - return; - } -#ifdef _WIN_32 - CharToOem(Msg,Msg); - - char OutMsg[MaxMsgSize],*OutPos=OutMsg; - for (int I=0;Msg[I]!=0;I++) - { - if (Msg[I]=='\n' && (I==0 || Msg[I-1]!='\r')) - *(OutPos++)='\r'; - *(OutPos++)=Msg[I]; - } - *OutPos=0; - strcpy(Msg,OutMsg); -#endif -#if defined(_UNIX) || defined(_EMX) - char OutMsg[MaxMsgSize],*OutPos=OutMsg; - for (int I=0;Msg[I]!=0;I++) - if (Msg[I]!='\r') - *(OutPos++)=Msg[I]; - *OutPos=0; - strcpy(Msg,OutMsg); -#endif - - OutFile.Write(Msg,strlen(Msg)); -// OutFile.Flush(); -} -#endif - - -#ifndef SILENT -void Alarm() -{ -#ifndef SFX_MODULE - if (Sound) - putchar('\007'); -#endif -} -#endif - - -#ifndef SILENT -#ifndef GUI -void GetPasswordText(char *Str,int MaxLength) -{ -#ifdef _WIN_32 - HANDLE hConIn=GetStdHandle(STD_INPUT_HANDLE); - HANDLE hConOut=GetStdHandle(STD_OUTPUT_HANDLE); - DWORD ConInMode,ConOutMode; - DWORD Read=0; - GetConsoleMode(hConIn,&ConInMode); - GetConsoleMode(hConOut,&ConOutMode); - SetConsoleMode(hConIn,ENABLE_LINE_INPUT); - SetConsoleMode(hConOut,ENABLE_PROCESSED_OUTPUT|ENABLE_WRAP_AT_EOL_OUTPUT); - ReadConsole(hConIn,Str,MaxLength-1,&Read,NULL); - Str[Read]=0; - OemToChar(Str,Str); - SetConsoleMode(hConIn,ConInMode); - SetConsoleMode(hConOut,ConOutMode); -#elif defined(_EMX) || defined(_BEOS) || defined(__sparc) || defined(sparc) || defined (__VMS) - fgets(Str,MaxLength-1,stdin); -#else - strncpyz(Str,getpass(""),MaxLength); -#endif - Str[MaxLength-1]=0; - RemoveLF(Str); -} -#endif -#endif - - -#if !defined(GUI) && !defined(SILENT) -unsigned int GetKey() -{ -#ifdef SILENT - return(0); -#else - char Str[80]; -#ifdef __GNUC__ - fgets(Str,sizeof(Str),stdin); - return(Str[0]); -#else - File SrcFile; - SrcFile.SetHandleType(FILE_HANDLESTD); - SrcFile.Read(Str,sizeof(Str)); - return(Str[0]); -#endif -#endif -} -#endif - - -#ifndef SILENT -bool GetPassword(PASSWORD_TYPE Type,const char *FileName,char *Password,int MaxLength) -{ - Alarm(); - while (true) - { - char PromptStr[NM+256]; -#if defined(_EMX) || defined(_BEOS) - strcpy(PromptStr,St(MAskPswEcho)); -#else - strcpy(PromptStr,St(MAskPsw)); -#endif - if (Type!=PASSWORD_GLOBAL) - { - strcat(PromptStr,St(MFor)); - char *NameOnly=PointToName(FileName); - if (strlen(PromptStr)+strlen(NameOnly)4 ? "\n":" "):", "); - int KeyPos=ItemKeyPos[I]; - for (int J=0;J>1)^0xEDB88320L : (C>>1); - CRCTab[I]=C; - } -} - - -uint CRC(uint StartCRC,const void *Addr,uint Size) -{ - if (CRCTab[1]==0) - InitCRC(); - byte *Data=(byte *)Addr; -#if defined(LITTLE_ENDIAN) && defined(PRESENT_INT32) && defined(ALLOW_NOT_ALIGNED_INT) - while (Size>0 && ((long)Data & 7)) - { - StartCRC=CRCTab[(byte)(StartCRC^Data[0])]^(StartCRC>>8); - Size--; - Data++; - } - while (Size>=8) - { - StartCRC^=*(uint32 *)Data; - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - StartCRC^=*(uint32 *)(Data+4); - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - StartCRC=CRCTab[(byte)StartCRC]^(StartCRC>>8); - Data+=8; - Size-=8; - } -#endif - for (int I=0;I>8); - return(StartCRC); -} - -#ifndef SFX_MODULE -ushort OldCRC(ushort StartCRC,const void *Addr,uint Size) -{ - byte *Data=(byte *)Addr; - for (int I=0;I>15))&0xffff; - } - return(StartCRC); -} -#endif diff --git a/src/bin/unrar/crc.hpp b/src/bin/unrar/crc.hpp deleted file mode 100644 index 47ee7e230b..0000000000 --- a/src/bin/unrar/crc.hpp +++ /dev/null @@ -1,10 +0,0 @@ -#ifndef _RAR_CRC_ -#define _RAR_CRC_ - -extern uint CRCTab[256]; - -void InitCRC(); -uint CRC(uint StartCRC,const void *Addr,uint Size); -ushort OldCRC(ushort StartCRC,const void *Addr,uint Size); - -#endif diff --git a/src/bin/unrar/crypt.cpp b/src/bin/unrar/crypt.cpp deleted file mode 100644 index 04a1d7086b..0000000000 --- a/src/bin/unrar/crypt.cpp +++ /dev/null @@ -1,381 +0,0 @@ -#include "rar.hpp" - -#ifndef SFX_MODULE -extern uint CRCTab[256]; -#endif - -#define NROUNDS 32 - -#define rol(x,n,xsize) (((x)<<(n)) | ((x)>>(xsize-(n)))) -#define ror(x,n,xsize) (((x)>>(n)) | ((x)<<(xsize-(n)))) - -#define substLong(t) ( (uint)SubstTable[(uint)t&255] | \ - ((uint)SubstTable[(int)(t>> 8)&255]<< 8) | \ - ((uint)SubstTable[(int)(t>>16)&255]<<16) | \ - ((uint)SubstTable[(int)(t>>24)&255]<<24) ) - -CryptKeyCacheItem CryptData::Cache[4]; -int CryptData::CachePos=0; - - -#ifndef SFX_MODULE -static byte InitSubstTable[256]={ - 215, 19,149, 35, 73,197,192,205,249, 28, 16,119, 48,221, 2, 42, - 232, 1,177,233, 14, 88,219, 25,223,195,244, 90, 87,239,153,137, - 255,199,147, 70, 92, 66,246, 13,216, 40, 62, 29,217,230, 86, 6, - 71, 24,171,196,101,113,218,123, 93, 91,163,178,202, 67, 44,235, - 107,250, 75,234, 49,167,125,211, 83,114,157,144, 32,193,143, 36, - 158,124,247,187, 89,214,141, 47,121,228, 61,130,213,194,174,251, - 97,110, 54,229,115, 57,152, 94,105,243,212, 55,209,245, 63, 11, - 164,200, 31,156, 81,176,227, 21, 76, 99,139,188,127, 17,248, 51, - 207,120,189,210, 8,226, 41, 72,183,203,135,165,166, 60, 98, 7, - 122, 38,155,170, 69,172,252,238, 39,134, 59,128,236, 27,240, 80, - 131, 3, 85,206,145, 79,154,142,159,220,201,133, 74, 64, 20,129, - 224,185,138,103,173,182, 43, 34,254, 82,198,151,231,180, 58, 10, - 118, 26,102, 12, 50,132, 22,191,136,111,162,179, 45, 4,148,108, - 161, 56, 78,126,242,222, 15,175,146, 23, 33,241,181,190, 77,225, - 0, 46,169,186, 68, 95,237, 65, 53,208,253,168, 9, 18,100, 52, - 116,184,160, 96,109, 37, 30,106,140,104,150, 5,204,117,112, 84 -}; -#endif - - - -void CryptData::DecryptBlock(byte *Buf,int Size) -{ - rin.blockDecrypt(Buf,Size,Buf); -} - - -#ifndef SFX_MODULE -void CryptData::EncryptBlock20(byte *Buf) -{ - uint A,B,C,D,T,TA,TB; -#if defined(BIG_ENDIAN) || !defined(PRESENT_INT32) || !defined(ALLOW_NOT_ALIGNED_INT) - A=((uint)Buf[0]|((uint)Buf[1]<<8)|((uint)Buf[2]<<16)|((uint)Buf[3]<<24))^Key[0]; - B=((uint)Buf[4]|((uint)Buf[5]<<8)|((uint)Buf[6]<<16)|((uint)Buf[7]<<24))^Key[1]; - C=((uint)Buf[8]|((uint)Buf[9]<<8)|((uint)Buf[10]<<16)|((uint)Buf[11]<<24))^Key[2]; - D=((uint)Buf[12]|((uint)Buf[13]<<8)|((uint)Buf[14]<<16)|((uint)Buf[15]<<24))^Key[3]; -#else - uint32 *BufPtr=(uint32 *)Buf; - A=BufPtr[0]^Key[0]; - B=BufPtr[1]^Key[1]; - C=BufPtr[2]^Key[2]; - D=BufPtr[3]^Key[3]; -#endif - for(int I=0;I>8); - Buf[2]=(byte)(C>>16); - Buf[3]=(byte)(C>>24); - D^=Key[1]; - Buf[4]=(byte)D; - Buf[5]=(byte)(D>>8); - Buf[6]=(byte)(D>>16); - Buf[7]=(byte)(D>>24); - A^=Key[2]; - Buf[8]=(byte)A; - Buf[9]=(byte)(A>>8); - Buf[10]=(byte)(A>>16); - Buf[11]=(byte)(A>>24); - B^=Key[3]; - Buf[12]=(byte)B; - Buf[13]=(byte)(B>>8); - Buf[14]=(byte)(B>>16); - Buf[15]=(byte)(B>>24); -#else - BufPtr[0]=C^Key[0]; - BufPtr[1]=D^Key[1]; - BufPtr[2]=A^Key[2]; - BufPtr[3]=B^Key[3]; -#endif - UpdKeys(Buf); -} - - -void CryptData::DecryptBlock20(byte *Buf) -{ - byte InBuf[16]; - uint A,B,C,D,T,TA,TB; -#if defined(BIG_ENDIAN) || !defined(PRESENT_INT32) || !defined(ALLOW_NOT_ALIGNED_INT) - A=((uint)Buf[0]|((uint)Buf[1]<<8)|((uint)Buf[2]<<16)|((uint)Buf[3]<<24))^Key[0]; - B=((uint)Buf[4]|((uint)Buf[5]<<8)|((uint)Buf[6]<<16)|((uint)Buf[7]<<24))^Key[1]; - C=((uint)Buf[8]|((uint)Buf[9]<<8)|((uint)Buf[10]<<16)|((uint)Buf[11]<<24))^Key[2]; - D=((uint)Buf[12]|((uint)Buf[13]<<8)|((uint)Buf[14]<<16)|((uint)Buf[15]<<24))^Key[3]; -#else - uint32 *BufPtr=(uint32 *)Buf; - A=BufPtr[0]^Key[0]; - B=BufPtr[1]^Key[1]; - C=BufPtr[2]^Key[2]; - D=BufPtr[3]^Key[3]; -#endif - memcpy(InBuf,Buf,sizeof(InBuf)); - for(int I=NROUNDS-1;I>=0;I--) - { - T=((C+rol(D,11,32))^Key[I&3]); - TA=A^substLong(T); - T=((D^rol(C,17,32))+Key[I&3]); - TB=B^substLong(T); - A=C; - B=D; - C=TA; - D=TB; - } -#if defined(BIG_ENDIAN) || !defined(PRESENT_INT32) || !defined(ALLOW_NOT_ALIGNED_INT) - C^=Key[0]; - Buf[0]=(byte)C; - Buf[1]=(byte)(C>>8); - Buf[2]=(byte)(C>>16); - Buf[3]=(byte)(C>>24); - D^=Key[1]; - Buf[4]=(byte)D; - Buf[5]=(byte)(D>>8); - Buf[6]=(byte)(D>>16); - Buf[7]=(byte)(D>>24); - A^=Key[2]; - Buf[8]=(byte)A; - Buf[9]=(byte)(A>>8); - Buf[10]=(byte)(A>>16); - Buf[11]=(byte)(A>>24); - B^=Key[3]; - Buf[12]=(byte)B; - Buf[13]=(byte)(B>>8); - Buf[14]=(byte)(B>>16); - Buf[15]=(byte)(B>>24); -#else - BufPtr[0]=C^Key[0]; - BufPtr[1]=D^Key[1]; - BufPtr[2]=A^Key[2]; - BufPtr[3]=B^Key[3]; -#endif - UpdKeys(InBuf); -} - - -void CryptData::UpdKeys(byte *Buf) -{ - for (int I=0;I<16;I+=4) - { - Key[0]^=CRCTab[Buf[I]]; - Key[1]^=CRCTab[Buf[I+1]]; - Key[2]^=CRCTab[Buf[I+2]]; - Key[3]^=CRCTab[Buf[I+3]]; - } -} - - -void CryptData::Swap(byte *Ch1,byte *Ch2) -{ - byte Ch=*Ch1; - *Ch1=*Ch2; - *Ch2=Ch; -} -#endif - - -void CryptData::SetCryptKeys(char *Password,byte *Salt,bool Encrypt,bool OldOnly,bool HandsOffHash) -{ - if (*Password==0) - return; - if (OldOnly) - { -#ifndef SFX_MODULE - if (CRCTab[1]==0) - InitCRC(); - byte Psw[MAXPASSWORD]; - SetOldKeys(Password); - Key[0]=0xD3A3B879L; - Key[1]=0x3F6D12F7L; - Key[2]=0x7515A235L; - Key[3]=0xA4E7F123L; - memset(Psw,0,sizeof(Psw)); -#if defined(_WIN_32) && !defined(GUI) - CharToOemBuff(Password,(char*)Psw,strlen(Password)); -#else - strncpyz((char *)Psw,Password,ASIZE(Psw)); -#endif - int PswLength=strlen(Password); - memcpy(SubstTable,InitSubstTable,sizeof(SubstTable)); - for (int J=0;J<256;J++) - for (int I=0;I>8); - PswNum[2]=(byte)(I>>16); - hash_process( &c, PswNum, 3, HandsOffHash); - if (I%(HashRounds/16)==0) - { - hash_context tempc=c; - uint32 digest[5]; - hash_final( &tempc, digest, HandsOffHash); - AESInit[I/(HashRounds/16)]=(byte)digest[4]; - } - } - uint32 digest[5]; - hash_final( &c, digest, HandsOffHash); - for (int I=0;I<4;I++) - for (int J=0;J<4;J++) - AESKey[I*4+J]=(byte)(digest[I]>>(J*8)); - - strcpy(Cache[CachePos].Password,Password); - if ((Cache[CachePos].SaltPresent=(Salt!=NULL))==true) - memcpy(Cache[CachePos].Salt,Salt,SALT_SIZE); - Cache[CachePos].HandsOffHash=HandsOffHash; - memcpy(Cache[CachePos].AESKey,AESKey,sizeof(AESKey)); - memcpy(Cache[CachePos].AESInit,AESInit,sizeof(AESInit)); - CachePos=(CachePos+1)%(sizeof(Cache)/sizeof(Cache[0])); - } - rin.init(Encrypt ? Rijndael::Encrypt : Rijndael::Decrypt,AESKey,AESInit); -} - - -#ifndef SFX_MODULE -void CryptData::SetOldKeys(char *Password) -{ - uint PswCRC=CRC(0xffffffff,Password,strlen(Password)); - OldKey[0]=PswCRC&0xffff; - OldKey[1]=(PswCRC>>16)&0xffff; - OldKey[2]=OldKey[3]=0; - PN1=PN2=PN3=0; - byte Ch; - while ((Ch=*Password)!=0) - { - PN1+=Ch; - PN2^=Ch; - PN3+=Ch; - PN3=(byte)rol(PN3,1,8); - OldKey[2]^=Ch^CRCTab[Ch]; - OldKey[3]+=Ch+(CRCTab[Ch]>>16); - Password++; - } -} - - -void CryptData::SetAV15Encryption() -{ - OldKey[0]=0x4765; - OldKey[1]=0x9021; - OldKey[2]=0x7382; - OldKey[3]=0x5215; -} - - -void CryptData::SetCmt13Encryption() -{ - PN1=0; - PN2=7; - PN3=77; -} - - -void CryptData::Crypt(byte *Data,uint Count,int Method) -{ - if (Method==OLD_DECODE) - Decode13(Data,Count); - else - if (Method==OLD_ENCODE) - Encode13(Data,Count); - else - Crypt15(Data,Count); -} - - -void CryptData::Encode13(byte *Data,uint Count) -{ - while (Count--) - { - PN2+=PN3; - PN1+=PN2; - *Data+=PN1; - Data++; - } -} - - -void CryptData::Decode13(byte *Data,uint Count) -{ - while (Count--) - { - PN2+=PN3; - PN1+=PN2; - *Data-=PN1; - Data++; - } -} - - -void CryptData::Crypt15(byte *Data,uint Count) -{ - while (Count--) - { - OldKey[0]+=0x1234; - OldKey[1]^=CRCTab[(OldKey[0] & 0x1fe)>>1]; - OldKey[2]-=CRCTab[(OldKey[0] & 0x1fe)>>1]>>16; - OldKey[0]^=OldKey[2]; - OldKey[3]=ror(OldKey[3]&0xffff,1,16)^OldKey[1]; - OldKey[3]=ror(OldKey[3]&0xffff,1,16); - OldKey[0]^=OldKey[3]; - *Data^=(byte)(OldKey[0]>>8); - Data++; - } -} -#endif - - diff --git a/src/bin/unrar/crypt.hpp b/src/bin/unrar/crypt.hpp deleted file mode 100644 index e70aaa3f73..0000000000 --- a/src/bin/unrar/crypt.hpp +++ /dev/null @@ -1,62 +0,0 @@ -#ifndef _RAR_CRYPT_ -#define _RAR_CRYPT_ - -enum { OLD_DECODE=0,OLD_ENCODE=1,NEW_CRYPT=2 }; - - -struct CryptKeyCacheItem -{ -#ifndef _SFX_RTL_ - CryptKeyCacheItem() - { - *Password=0; - } - - ~CryptKeyCacheItem() - { - memset(AESKey,0,sizeof(AESKey)); - memset(AESInit,0,sizeof(AESInit)); - memset(Password,0,sizeof(Password)); - } -#endif - byte AESKey[16],AESInit[16]; - char Password[MAXPASSWORD]; - bool SaltPresent; - byte Salt[SALT_SIZE]; - bool HandsOffHash; -}; - -class CryptData -{ - private: - void Encode13(byte *Data,uint Count); - void Decode13(byte *Data,uint Count); - void Crypt15(byte *Data,uint Count); - void UpdKeys(byte *Buf); - void Swap(byte *Ch1,byte *Ch2); - void SetOldKeys(char *Password); - - Rijndael rin; - - byte SubstTable[256]; - uint Key[4]; - ushort OldKey[4]; - byte PN1,PN2,PN3; - - byte AESKey[16],AESInit[16]; - - static CryptKeyCacheItem Cache[4]; - static int CachePos; - public: - void SetCryptKeys(char *Password,byte *Salt,bool Encrypt,bool OldOnly,bool HandsOffHash); - void SetAV15Encryption(); - void SetCmt13Encryption(); - void EncryptBlock20(byte *Buf); - void DecryptBlock20(byte *Buf); - void EncryptBlock(byte *Buf,int Size); - void DecryptBlock(byte *Buf,int Size); - void Crypt(byte *Data,uint Count,int Method); - static void SetSalt(byte *Salt,int SaltSize); -}; - -#endif diff --git a/src/bin/unrar/dll.cpp b/src/bin/unrar/dll.cpp deleted file mode 100644 index f1a2cc90ea..0000000000 --- a/src/bin/unrar/dll.cpp +++ /dev/null @@ -1,365 +0,0 @@ -#include "rar.hpp" -#include "dll.hpp" - -static int RarErrorToDll(int ErrCode); - -struct DataSet -{ - CommandData Cmd; - CmdExtract Extract; - Archive Arc; - int OpenMode; - int HeaderSize; - - DataSet():Arc(&Cmd) {}; -}; - - -HANDLE PASCAL RAROpenArchive(struct RAROpenArchiveData *r) -{ - RAROpenArchiveDataEx rx; - memset(&rx,0,sizeof(rx)); - rx.ArcName=r->ArcName; - rx.OpenMode=r->OpenMode; - rx.CmtBuf=r->CmtBuf; - rx.CmtBufSize=r->CmtBufSize; - HANDLE hArc=RAROpenArchiveEx(&rx); - r->OpenResult=rx.OpenResult; - r->CmtSize=rx.CmtSize; - r->CmtState=rx.CmtState; - return(hArc); -} - - -HANDLE PASCAL RAROpenArchiveEx(struct RAROpenArchiveDataEx *r) -{ - try - { - r->OpenResult=0; - DataSet *Data=new DataSet; - Data->Cmd.DllError=0; - Data->OpenMode=r->OpenMode; - Data->Cmd.FileArgs->AddString("*"); - - char an[NM]; - if (r->ArcName==NULL && r->ArcNameW!=NULL) - { - WideToChar(r->ArcNameW,an,NM); - r->ArcName=an; - } - - Data->Cmd.AddArcName(r->ArcName,r->ArcNameW); - Data->Cmd.Overwrite=OVERWRITE_ALL; - Data->Cmd.VersionControl=1; - if (!Data->Arc.Open(r->ArcName,r->ArcNameW)) - { - r->OpenResult=ERAR_EOPEN; - delete Data; - return(NULL); - } - if (!Data->Arc.IsArchive(false)) - { - r->OpenResult=Data->Cmd.DllError!=0 ? Data->Cmd.DllError:ERAR_BAD_ARCHIVE; - delete Data; - return(NULL); - } - r->Flags=Data->Arc.NewMhd.Flags; - Array CmtData; - if (r->CmtBufSize!=0 && Data->Arc.GetComment(&CmtData,NULL)) - { - r->Flags|=2; - int Size=CmtData.Size()+1; - r->CmtState=Size>r->CmtBufSize ? ERAR_SMALL_BUF:1; - r->CmtSize=Min(Size,r->CmtBufSize); - memcpy(r->CmtBuf,&CmtData[0],r->CmtSize-1); - if (Size<=r->CmtBufSize) - r->CmtBuf[r->CmtSize-1]=0; - } - else - r->CmtState=r->CmtSize=0; - if (Data->Arc.Signed) - r->Flags|=0x20; - Data->Extract.ExtractArchiveInit(&Data->Cmd,Data->Arc); - return((HANDLE)Data); - } - catch (int ErrCode) - { - r->OpenResult=RarErrorToDll(ErrCode); - return(NULL); - } -} - - -int PASCAL RARCloseArchive(HANDLE hArcData) -{ - DataSet *Data=(DataSet *)hArcData; - bool Success=Data==NULL ? false:Data->Arc.Close(); - delete Data; - return(Success ? 0:ERAR_ECLOSE); -} - - -int PASCAL RARReadHeader(HANDLE hArcData,struct RARHeaderData *D) -{ - DataSet *Data=(DataSet *)hArcData; - try - { - if ((Data->HeaderSize=Data->Arc.SearchBlock(FILE_HEAD))<=0) - { - if (Data->Arc.Volume && Data->Arc.GetHeaderType()==ENDARC_HEAD && - (Data->Arc.EndArcHead.Flags & EARC_NEXT_VOLUME)) - if (MergeArchive(Data->Arc,NULL,false,'L')) - { - Data->Extract.SignatureFound=false; - Data->Arc.Seek(Data->Arc.CurBlockPos,SEEK_SET); - return(RARReadHeader(hArcData,D)); - } - else - return(ERAR_EOPEN); - return(Data->Arc.BrokenFileHeader ? ERAR_BAD_DATA:ERAR_END_ARCHIVE); - } - if (Data->OpenMode==RAR_OM_LIST && (Data->Arc.NewLhd.Flags & LHD_SPLIT_BEFORE)) - { - int Code=RARProcessFile(hArcData,RAR_SKIP,NULL,NULL); - if (Code==0) - return(RARReadHeader(hArcData,D)); - else - return(Code); - } - strncpyz(D->ArcName,Data->Arc.FileName,ASIZE(D->ArcName)); - strncpyz(D->FileName,Data->Arc.NewLhd.FileName,ASIZE(D->FileName)); - D->Flags=Data->Arc.NewLhd.Flags; - D->PackSize=Data->Arc.NewLhd.PackSize; - D->UnpSize=Data->Arc.NewLhd.UnpSize; - D->HostOS=Data->Arc.NewLhd.HostOS; - D->FileCRC=Data->Arc.NewLhd.FileCRC; - D->FileTime=Data->Arc.NewLhd.FileTime; - D->UnpVer=Data->Arc.NewLhd.UnpVer; - D->Method=Data->Arc.NewLhd.Method; - D->FileAttr=Data->Arc.NewLhd.FileAttr; - D->CmtSize=0; - D->CmtState=0; - } - catch (int ErrCode) - { - return(RarErrorToDll(ErrCode)); - } - return(0); -} - - -int PASCAL RARReadHeaderEx(HANDLE hArcData,struct RARHeaderDataEx *D) -{ - DataSet *Data=(DataSet *)hArcData; - try - { - if ((Data->HeaderSize=Data->Arc.SearchBlock(FILE_HEAD))<=0) - { - if (Data->Arc.Volume && Data->Arc.GetHeaderType()==ENDARC_HEAD && - (Data->Arc.EndArcHead.Flags & EARC_NEXT_VOLUME)) - if (MergeArchive(Data->Arc,NULL,false,'L')) - { - Data->Extract.SignatureFound=false; - Data->Arc.Seek(Data->Arc.CurBlockPos,SEEK_SET); - return(RARReadHeaderEx(hArcData,D)); - } - else - return(ERAR_EOPEN); - return(Data->Arc.BrokenFileHeader ? ERAR_BAD_DATA:ERAR_END_ARCHIVE); - } - if (Data->OpenMode==RAR_OM_LIST && (Data->Arc.NewLhd.Flags & LHD_SPLIT_BEFORE)) - { - int Code=RARProcessFile(hArcData,RAR_SKIP,NULL,NULL); - if (Code==0) - return(RARReadHeaderEx(hArcData,D)); - else - return(Code); - } - strncpyz(D->ArcName,Data->Arc.FileName,ASIZE(D->ArcName)); - if (*Data->Arc.FileNameW) - strncpyw(D->ArcNameW,Data->Arc.FileNameW,sizeof(D->ArcNameW)); - else - CharToWide(Data->Arc.FileName,D->ArcNameW); - strncpyz(D->FileName,Data->Arc.NewLhd.FileName,ASIZE(D->FileName)); - if (*Data->Arc.NewLhd.FileNameW) - strncpyw(D->FileNameW,Data->Arc.NewLhd.FileNameW,sizeof(D->FileNameW)); - else - { -#ifdef _WIN_32 - char AnsiName[NM]; - OemToChar(Data->Arc.NewLhd.FileName,AnsiName); - CharToWide(AnsiName,D->FileNameW); -#else - CharToWide(Data->Arc.NewLhd.FileName,D->FileNameW); -#endif - } - D->Flags=Data->Arc.NewLhd.Flags; - D->PackSize=Data->Arc.NewLhd.PackSize; - D->PackSizeHigh=Data->Arc.NewLhd.HighPackSize; - D->UnpSize=Data->Arc.NewLhd.UnpSize; - D->UnpSizeHigh=Data->Arc.NewLhd.HighUnpSize; - D->HostOS=Data->Arc.NewLhd.HostOS; - D->FileCRC=Data->Arc.NewLhd.FileCRC; - D->FileTime=Data->Arc.NewLhd.FileTime; - D->UnpVer=Data->Arc.NewLhd.UnpVer; - D->Method=Data->Arc.NewLhd.Method; - D->FileAttr=Data->Arc.NewLhd.FileAttr; - D->CmtSize=0; - D->CmtState=0; - } - catch (int ErrCode) - { - return(RarErrorToDll(ErrCode)); - } - return(0); -} - - -int PASCAL ProcessFile(HANDLE hArcData,int Operation,char *DestPath,char *DestName,wchar *DestPathW,wchar *DestNameW) -{ - DataSet *Data=(DataSet *)hArcData; - try - { - Data->Cmd.DllError=0; - if (Data->OpenMode==RAR_OM_LIST || Operation==RAR_SKIP && !Data->Arc.Solid) - { - if (/*Data->OpenMode==RAR_OM_LIST && */Data->Arc.Volume && - Data->Arc.GetHeaderType()==FILE_HEAD && - (Data->Arc.NewLhd.Flags & LHD_SPLIT_AFTER)!=0) - if (MergeArchive(Data->Arc,NULL,false,'L')) - { - Data->Extract.SignatureFound=false; - Data->Arc.Seek(Data->Arc.CurBlockPos,SEEK_SET); - return(0); - } - else - return(ERAR_EOPEN); - Data->Arc.SeekToNext(); - } - else - { - Data->Cmd.DllOpMode=Operation; - - if (DestPath!=NULL || DestName!=NULL) - { -#ifdef _WIN_32 - OemToChar(NullToEmpty(DestPath),Data->Cmd.ExtrPath); -#else - strcpy(Data->Cmd.ExtrPath,NullToEmpty(DestPath)); -#endif - AddEndSlash(Data->Cmd.ExtrPath); -#ifdef _WIN_32 - OemToChar(NullToEmpty(DestName),Data->Cmd.DllDestName); -#else - strcpy(Data->Cmd.DllDestName,NullToEmpty(DestName)); -#endif - } - else - { - *Data->Cmd.ExtrPath=0; - *Data->Cmd.DllDestName=0; - } - - if (DestPathW!=NULL || DestNameW!=NULL) - { - strncpyw(Data->Cmd.ExtrPathW,NullToEmpty(DestPathW),NM-2); - AddEndSlash(Data->Cmd.ExtrPathW); - strncpyw(Data->Cmd.DllDestNameW,NullToEmpty(DestNameW),NM-1); - } - else - { - *Data->Cmd.ExtrPathW=0; - *Data->Cmd.DllDestNameW=0; - } - - strcpy(Data->Cmd.Command,Operation==RAR_EXTRACT ? "X":"T"); - Data->Cmd.Test=Operation!=RAR_EXTRACT; - bool Repeat=false; - Data->Extract.ExtractCurrentFile(&Data->Cmd,Data->Arc,Data->HeaderSize,Repeat); - - while (Data->Arc.ReadHeader()!=0 && Data->Arc.GetHeaderType()==NEWSUB_HEAD) - { - Data->Extract.ExtractCurrentFile(&Data->Cmd,Data->Arc,Data->HeaderSize,Repeat); - Data->Arc.SeekToNext(); - } - Data->Arc.Seek(Data->Arc.CurBlockPos,SEEK_SET); - } - } - catch (int ErrCode) - { - return(RarErrorToDll(ErrCode)); - } - return(Data->Cmd.DllError); -} - - -int PASCAL RARProcessFile(HANDLE hArcData,int Operation,char *DestPath,char *DestName) -{ - return(ProcessFile(hArcData,Operation,DestPath,DestName,NULL,NULL)); -} - - -int PASCAL RARProcessFileW(HANDLE hArcData,int Operation,wchar *DestPath,wchar *DestName) -{ - return(ProcessFile(hArcData,Operation,NULL,NULL,DestPath,DestName)); -} - - -void PASCAL RARSetChangeVolProc(HANDLE hArcData,CHANGEVOLPROC ChangeVolProc) -{ - DataSet *Data=(DataSet *)hArcData; - Data->Cmd.ChangeVolProc=ChangeVolProc; -} - - -void PASCAL RARSetCallback(HANDLE hArcData,UNRARCALLBACK Callback,LONG UserData) -{ - DataSet *Data=(DataSet *)hArcData; - Data->Cmd.Callback=Callback; - Data->Cmd.UserData=UserData; -} - - -void PASCAL RARSetProcessDataProc(HANDLE hArcData,PROCESSDATAPROC ProcessDataProc) -{ - DataSet *Data=(DataSet *)hArcData; - Data->Cmd.ProcessDataProc=ProcessDataProc; -} - -#ifndef NOCRYPT -void PASCAL RARSetPassword(HANDLE hArcData,char *Password) -{ - DataSet *Data=(DataSet *)hArcData; - strncpyz(Data->Cmd.Password,Password,ASIZE(Data->Cmd.Password)); -} -#endif - - -int PASCAL RARGetDllVersion() -{ - return(RAR_DLL_VERSION); -} - - -static int RarErrorToDll(int ErrCode) -{ - switch(ErrCode) - { - case FATAL_ERROR: - return(ERAR_EREAD); - case CRC_ERROR: - return(ERAR_BAD_DATA); - case WRITE_ERROR: - return(ERAR_EWRITE); - case OPEN_ERROR: - return(ERAR_EOPEN); - case CREATE_ERROR: - return(ERAR_ECREATE); - case MEMORY_ERROR: - return(ERAR_NO_MEMORY); - case SUCCESS: - return(0); - default: - return(ERAR_UNKNOWN); - } -} diff --git a/src/bin/unrar/dll.def b/src/bin/unrar/dll.def deleted file mode 100644 index 660f69bf6e..0000000000 --- a/src/bin/unrar/dll.def +++ /dev/null @@ -1,12 +0,0 @@ -EXPORTS - RAROpenArchive - RAROpenArchiveEx - RARCloseArchive - RARReadHeader - RARReadHeaderEx - RARProcessFile - RARSetCallback - RARSetChangeVolProc - RARSetProcessDataProc - RARSetPassword - RARGetDllVersion diff --git a/src/bin/unrar/dll.hpp b/src/bin/unrar/dll.hpp deleted file mode 100644 index 4b677441f3..0000000000 --- a/src/bin/unrar/dll.hpp +++ /dev/null @@ -1,138 +0,0 @@ -#ifndef _UNRAR_DLL_ -#define _UNRAR_DLL_ - -#define ERAR_END_ARCHIVE 10 -#define ERAR_NO_MEMORY 11 -#define ERAR_BAD_DATA 12 -#define ERAR_BAD_ARCHIVE 13 -#define ERAR_UNKNOWN_FORMAT 14 -#define ERAR_EOPEN 15 -#define ERAR_ECREATE 16 -#define ERAR_ECLOSE 17 -#define ERAR_EREAD 18 -#define ERAR_EWRITE 19 -#define ERAR_SMALL_BUF 20 -#define ERAR_UNKNOWN 21 -#define ERAR_MISSING_PASSWORD 22 - -#define RAR_OM_LIST 0 -#define RAR_OM_EXTRACT 1 - -#define RAR_SKIP 0 -#define RAR_TEST 1 -#define RAR_EXTRACT 2 - -#define RAR_VOL_ASK 0 -#define RAR_VOL_NOTIFY 1 - -#define RAR_DLL_VERSION 4 - -#ifdef _UNIX -#define CALLBACK -#define PASCAL -#define LONG long -#define HANDLE void * -#define UINT unsigned int -#endif - -struct RARHeaderData -{ - char ArcName[260]; - char FileName[260]; - unsigned int Flags; - unsigned int PackSize; - unsigned int UnpSize; - unsigned int HostOS; - unsigned int FileCRC; - unsigned int FileTime; - unsigned int UnpVer; - unsigned int Method; - unsigned int FileAttr; - char *CmtBuf; - unsigned int CmtBufSize; - unsigned int CmtSize; - unsigned int CmtState; -}; - - -struct RARHeaderDataEx -{ - char ArcName[1024]; - wchar_t ArcNameW[1024]; - char FileName[1024]; - wchar_t FileNameW[1024]; - unsigned int Flags; - unsigned int PackSize; - unsigned int PackSizeHigh; - unsigned int UnpSize; - unsigned int UnpSizeHigh; - unsigned int HostOS; - unsigned int FileCRC; - unsigned int FileTime; - unsigned int UnpVer; - unsigned int Method; - unsigned int FileAttr; - char *CmtBuf; - unsigned int CmtBufSize; - unsigned int CmtSize; - unsigned int CmtState; - unsigned int Reserved[1024]; -}; - - -struct RAROpenArchiveData -{ - char *ArcName; - unsigned int OpenMode; - unsigned int OpenResult; - char *CmtBuf; - unsigned int CmtBufSize; - unsigned int CmtSize; - unsigned int CmtState; -}; - -struct RAROpenArchiveDataEx -{ - char *ArcName; - wchar_t *ArcNameW; - unsigned int OpenMode; - unsigned int OpenResult; - char *CmtBuf; - unsigned int CmtBufSize; - unsigned int CmtSize; - unsigned int CmtState; - unsigned int Flags; - unsigned int Reserved[32]; -}; - -enum UNRARCALLBACK_MESSAGES { - UCM_CHANGEVOLUME,UCM_PROCESSDATA,UCM_NEEDPASSWORD -}; - -typedef int (CALLBACK *UNRARCALLBACK)(UINT msg,LONG UserData,LONG P1,LONG P2); - -typedef int (PASCAL *CHANGEVOLPROC)(char *ArcName,int Mode); -typedef int (PASCAL *PROCESSDATAPROC)(unsigned char *Addr,int Size); - -#ifdef __cplusplus -extern "C" { -#endif - -HANDLE PASCAL RAROpenArchive(struct RAROpenArchiveData *ArchiveData); -HANDLE PASCAL RAROpenArchiveEx(struct RAROpenArchiveDataEx *ArchiveData); -int PASCAL RARCloseArchive(HANDLE hArcData); -int PASCAL RARReadHeader(HANDLE hArcData,struct RARHeaderData *HeaderData); -int PASCAL RARReadHeaderEx(HANDLE hArcData,struct RARHeaderDataEx *HeaderData); -int PASCAL RARProcessFile(HANDLE hArcData,int Operation,char *DestPath,char *DestName); -int PASCAL RARProcessFileW(HANDLE hArcData,int Operation,wchar_t *DestPath,wchar_t *DestName); -void PASCAL RARSetCallback(HANDLE hArcData,UNRARCALLBACK Callback,LONG UserData); -void PASCAL RARSetChangeVolProc(HANDLE hArcData,CHANGEVOLPROC ChangeVolProc); -void PASCAL RARSetProcessDataProc(HANDLE hArcData,PROCESSDATAPROC ProcessDataProc); -void PASCAL RARSetPassword(HANDLE hArcData,char *Password); -int PASCAL RARGetDllVersion(); - -#ifdef __cplusplus -} -#endif - -#endif diff --git a/src/bin/unrar/encname.cpp b/src/bin/unrar/encname.cpp deleted file mode 100644 index 6f57cd912b..0000000000 --- a/src/bin/unrar/encname.cpp +++ /dev/null @@ -1,57 +0,0 @@ -#include "rar.hpp" - -EncodeFileName::EncodeFileName() -{ - Flags=0; - FlagBits=0; - FlagsPos=0; - DestSize=0; -} - - - - -void EncodeFileName::Decode(char *Name,byte *EncName,int EncSize,wchar *NameW, - int MaxDecSize) -{ - int EncPos=0,DecPos=0; - byte HighByte=EncName[EncPos++]; - while (EncPos>6) - { - case 0: - NameW[DecPos++]=EncName[EncPos++]; - break; - case 1: - NameW[DecPos++]=EncName[EncPos++]+(HighByte<<8); - break; - case 2: - NameW[DecPos++]=EncName[EncPos]+(EncName[EncPos+1]<<8); - EncPos+=2; - break; - case 3: - { - int Length=EncName[EncPos++]; - if (Length & 0x80) - { - byte Correction=EncName[EncPos++]; - for (Length=(Length&0x7f)+2;Length>0 && DecPos0 && DecPosMAXPATH) - { - Log(ArcName && *ArcName ? ArcName:NULL,St(MMaxPathLimit),MAXPATH); - } - } -#endif - SysErrMsg(); -#endif -} - - -void ErrorHandler::ReadErrorMsg(const char *ArcName,const char *FileName) -{ -#ifndef SILENT - ErrMsg(ArcName,St(MErrRead),FileName); - SysErrMsg(); -#endif -} - - -void ErrorHandler::WriteErrorMsg(const char *ArcName,const char *FileName) -{ -#ifndef SILENT - ErrMsg(ArcName,St(MErrWrite),FileName); - SysErrMsg(); -#endif -} - - -void ErrorHandler::Exit(int ExitCode) -{ -#ifndef SFX_MODULE - Alarm(); -#endif - Throw(ExitCode); -} - - -#ifndef GUI -void ErrorHandler::ErrMsg(const char *ArcName,const char *fmt,...) -{ - safebuf char Msg[NM+1024]; - va_list argptr; - va_start(argptr,fmt); - vsprintf(Msg,fmt,argptr); - va_end(argptr); -#ifdef _WIN_32 - if (UserBreak) - Sleep(5000); -#endif - Alarm(); - if (*Msg) - { - Log(ArcName,"\n%s",Msg); - mprintf("\n%s\n",St(MProgAborted)); - } -} -#endif - - -void ErrorHandler::SetErrorCode(int Code) -{ - switch(Code) - { - case WARNING: - case USER_BREAK: - if (ExitCode==SUCCESS) - ExitCode=Code; - break; - case FATAL_ERROR: - if (ExitCode==SUCCESS || ExitCode==WARNING) - ExitCode=FATAL_ERROR; - break; - default: - ExitCode=Code; - break; - } - ErrCount++; -} - - -#if !defined(GUI) && !defined(_SFX_RTL_) -#ifdef _WIN_32 -BOOL __stdcall ProcessSignal(DWORD SigType) -#else -#if defined(__sun) -extern "C" -#endif -void _stdfunction ProcessSignal(int SigType) -#endif -{ -#ifdef _WIN_32 - if (SigType==CTRL_LOGOFF_EVENT) - return(TRUE); -#endif - UserBreak=true; - mprintf(St(MBreak)); - for (int I=0;!File::RemoveCreated() && I<3;I++) - { -#ifdef _WIN_32 - Sleep(100); -#endif - } -#if defined(USE_RC) && !defined(SFX_MODULE) && !defined(_WIN_CE) - ExtRes.UnloadDLL(); -#endif - exit(USER_BREAK); -#ifdef _WIN_32 - return(TRUE); -#endif -} -#endif - - -void ErrorHandler::SetSignalHandlers(bool Enable) -{ - EnableBreak=Enable; -#if !defined(GUI) && !defined(_SFX_RTL_) -#ifdef _WIN_32 - SetConsoleCtrlHandler(Enable ? ProcessSignal:NULL,TRUE); -// signal(SIGBREAK,Enable ? ProcessSignal:SIG_IGN); -#else - signal(SIGINT,Enable ? ProcessSignal:SIG_IGN); - signal(SIGTERM,Enable ? ProcessSignal:SIG_IGN); -#endif -#endif -} - - -void ErrorHandler::Throw(int Code) -{ - if (Code==USER_BREAK && !EnableBreak) - return; - ErrHandler.SetErrorCode(Code); -#ifdef ALLOW_EXCEPTIONS - throw Code; -#else - File::RemoveCreated(); - exit(Code); -#endif -} - - -void ErrorHandler::SysErrMsg() -{ -#if !defined(SFX_MODULE) && !defined(SILENT) -#ifdef _WIN_32 - #define STRCHR strchr - #define ERRCHAR char - ERRCHAR *lpMsgBuf=NULL; - int ErrType=GetLastError(); - if (ErrType!=0 && FormatMessage(FORMAT_MESSAGE_ALLOCATE_BUFFER|FORMAT_MESSAGE_FROM_SYSTEM, - NULL,ErrType,MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), - (LPTSTR)&lpMsgBuf,0,NULL)) - { - ERRCHAR *CurMsg=lpMsgBuf; - while (CurMsg!=NULL) - { - while (*CurMsg=='\r' || *CurMsg=='\n') - CurMsg++; - if (*CurMsg==0) - break; - ERRCHAR *EndMsg=STRCHR(CurMsg,'\r'); - if (EndMsg==NULL) - EndMsg=STRCHR(CurMsg,'\n'); - if (EndMsg!=NULL) - { - *EndMsg=0; - EndMsg++; - } - Log(NULL,"\n%s",CurMsg); - CurMsg=EndMsg; - } - } - LocalFree( lpMsgBuf ); -#endif - -#if defined(_UNIX) || defined(_EMX) - char *err=strerror(errno); - if (err!=NULL) - Log(NULL,"\n%s",err); -#endif - -#endif -} - - - - diff --git a/src/bin/unrar/errhnd.hpp b/src/bin/unrar/errhnd.hpp deleted file mode 100644 index 732243ceee..0000000000 --- a/src/bin/unrar/errhnd.hpp +++ /dev/null @@ -1,62 +0,0 @@ -#ifndef _RAR_ERRHANDLER_ -#define _RAR_ERRHANDLER_ - -#if (defined(GUI) || !defined(_WIN_32)) && !defined(SFX_MODULE) && !defined(_WIN_CE) || defined(RARDLL) -#define ALLOW_EXCEPTIONS -#endif - - - -#define rarmalloc malloc -#define rarcalloc calloc -#define rarrealloc realloc -#define rarfree free -#define rarstrdup strdup - - - -enum { SUCCESS,WARNING,FATAL_ERROR,CRC_ERROR,LOCK_ERROR,WRITE_ERROR, - OPEN_ERROR,USER_ERROR,MEMORY_ERROR,CREATE_ERROR,USER_BREAK=255}; - -class ErrorHandler -{ - private: - void ErrMsg(const char *ArcName,const char *fmt,...); - - int ExitCode; - int ErrCount; - bool EnableBreak; - bool Silent; - bool DoShutdown; - public: - ErrorHandler(); - void Clean(); - void MemoryError(); - void OpenError(const char *FileName); - void CloseError(const char *FileName); - void ReadError(const char *FileName); - bool AskRepeatRead(const char *FileName); - void WriteError(const char *ArcName,const char *FileName); - void WriteErrorFAT(const char *FileName); - bool AskRepeatWrite(const char *FileName); - void SeekError(const char *FileName); - void GeneralErrMsg(const char *Msg); - void MemoryErrorMsg(); - void OpenErrorMsg(const char *FileName); - void OpenErrorMsg(const char *ArcName,const char *FileName); - void CreateErrorMsg(const char *FileName); - void CreateErrorMsg(const char *ArcName,const char *FileName); - void ReadErrorMsg(const char *ArcName,const char *FileName); - void WriteErrorMsg(const char *ArcName,const char *FileName); - void Exit(int ExitCode); - void SetErrorCode(int Code); - int GetErrorCode() {return(ExitCode);} - int GetErrorCount() {return(ErrCount);} - void SetSignalHandlers(bool Enable); - void Throw(int Code); - void SetSilent(bool Mode) {Silent=Mode;}; - void SetShutdown(bool Mode) {DoShutdown=Mode;}; - void SysErrMsg(); -}; - -#endif diff --git a/src/bin/unrar/extinfo.cpp b/src/bin/unrar/extinfo.cpp deleted file mode 100644 index 13239fe72c..0000000000 --- a/src/bin/unrar/extinfo.cpp +++ /dev/null @@ -1,76 +0,0 @@ -#include "rar.hpp" - -#ifdef _WIN_32 -#include "win32acl.cpp" -#include "win32stm.cpp" -#endif -#ifdef _BEOS -#include "beosea.cpp" -#endif -#if defined(_EMX) && !defined(_DJGPP) -#include "os2ea.cpp" -#endif -#ifdef _UNIX -#include "uowners.cpp" -#endif - - - -#ifndef SFX_MODULE -void SetExtraInfo(CommandData *Cmd,Archive &Arc,char *Name,wchar *NameW) -{ - switch(Arc.SubBlockHead.SubType) - { -#if defined(_EMX) && !defined(_DJGPP) - case EA_HEAD: - if (Cmd->ProcessEA) - ExtractOS2EA(Arc,Name); - break; -#endif -#ifdef _UNIX - case UO_HEAD: - if (Cmd->ProcessOwners) - ExtractUnixOwner(Arc,Name); - break; -#endif -#ifdef _BEOS - case BEEA_HEAD: - if (Cmd->ProcessEA) - ExtractBeEA(Arc,Name); - break; -#endif -#ifdef _WIN_32 - case NTACL_HEAD: - if (Cmd->ProcessOwners) - ExtractACL(Arc,Name,NameW); - break; - case STREAM_HEAD: - ExtractStreams(Arc,Name,NameW); - break; -#endif - } -} -#endif - - -void SetExtraInfoNew(CommandData *Cmd,Archive &Arc,char *Name,wchar *NameW) -{ -#if defined(_EMX) && !defined(_DJGPP) - if (Cmd->ProcessEA && Arc.SubHead.CmpName(SUBHEAD_TYPE_OS2EA)) - ExtractOS2EANew(Arc,Name); -#endif -#ifdef _UNIX - if (Cmd->ProcessOwners && Arc.SubHead.CmpName(SUBHEAD_TYPE_UOWNER)) - ExtractUnixOwnerNew(Arc,Name); -#endif -#ifdef _BEOS - if (Cmd->ProcessEA && Arc.SubHead.CmpName(SUBHEAD_TYPE_UOWNER)) - ExtractUnixOwnerNew(Arc,Name); -#endif -#ifdef _WIN_32 - if (Cmd->ProcessOwners && Arc.SubHead.CmpName(SUBHEAD_TYPE_ACL)) - ExtractACLNew(Arc,Name,NameW); - if (Arc.SubHead.CmpName(SUBHEAD_TYPE_STREAM)) - ExtractStreamsNew(Arc,Name,NameW); -#endif -} diff --git a/src/bin/unrar/extinfo.hpp b/src/bin/unrar/extinfo.hpp deleted file mode 100644 index db7cea53f8..0000000000 --- a/src/bin/unrar/extinfo.hpp +++ /dev/null @@ -1,8 +0,0 @@ -#ifndef _RAR_EXTINFO_ -#define _RAR_EXTINFO_ - - -void SetExtraInfo(CommandData *Cmd,Archive &Arc,char *Name,wchar *NameW); -void SetExtraInfoNew(CommandData *Cmd,Archive &Arc,char *Name,wchar *NameW); - -#endif diff --git a/src/bin/unrar/extract.cpp b/src/bin/unrar/extract.cpp deleted file mode 100644 index e9d75173ba..0000000000 --- a/src/bin/unrar/extract.cpp +++ /dev/null @@ -1,873 +0,0 @@ -#include "rar.hpp" - -CmdExtract::CmdExtract() -{ - TotalFileCount=0; - *Password=0; - Unp=new Unpack(&DataIO); - Unp->Init(NULL); -} - - -CmdExtract::~CmdExtract() -{ - delete Unp; - memset(Password,0,sizeof(Password)); -} - - -void CmdExtract::DoExtract(CommandData *Cmd) -{ - PasswordCancelled=false; - DataIO.SetCurrentCommand(*Cmd->Command); - - struct FindData FD; - while (Cmd->GetArcName(ArcName,ArcNameW,sizeof(ArcName))) - if (FindFile::FastFind(ArcName,ArcNameW,&FD)) - DataIO.TotalArcSize+=FD.Size; - Cmd->ArcNames->Rewind(); - while (Cmd->GetArcName(ArcName,ArcNameW,sizeof(ArcName))) - { - while (true) - { - char PrevCmdPassword[MAXPASSWORD]; - strcpy(PrevCmdPassword,Cmd->Password); - - EXTRACT_ARC_CODE Code=ExtractArchive(Cmd); - -/* - restore Cmd->Password which could be changed in IsArchive() call - for next header encrypted archive -*/ - strcpy(Cmd->Password,PrevCmdPassword); - - if (Code!=EXTRACT_ARC_REPEAT) - break; - } - if (FindFile::FastFind(ArcName,ArcNameW,&FD)) - DataIO.ProcessedArcSize+=FD.Size; - } - - if (TotalFileCount==0 && *Cmd->Command!='I') - { - if (!PasswordCancelled) - { - mprintf(St(MExtrNoFiles)); - } - ErrHandler.SetErrorCode(WARNING); - } -#ifndef GUI - else - if (!Cmd->DisableDone) - if (*Cmd->Command=='I') - mprintf(St(MDone)); - else - if (ErrHandler.GetErrorCount()==0) - mprintf(St(MExtrAllOk)); - else - mprintf(St(MExtrTotalErr),ErrHandler.GetErrorCount()); -#endif -} - - -void CmdExtract::ExtractArchiveInit(CommandData *Cmd,Archive &Arc) -{ - DataIO.UnpArcSize=Arc.FileLength(); - - FileCount=0; - MatchedArgs=0; -#ifndef SFX_MODULE - FirstFile=true; -#endif - - if (*Cmd->Password!=0) - strcpy(Password,Cmd->Password); - PasswordAll=(*Cmd->Password!=0); - - DataIO.UnpVolume=false; - - PrevExtracted=false; - SignatureFound=false; - AllMatchesExact=true; - ReconstructDone=false; -} - - -EXTRACT_ARC_CODE CmdExtract::ExtractArchive(CommandData *Cmd) -{ - Archive Arc(Cmd); - if (!Arc.WOpen(ArcName,ArcNameW)) - { - ErrHandler.SetErrorCode(OPEN_ERROR); - return(EXTRACT_ARC_NEXT); - } - - if (!Arc.IsArchive(true)) - { -#ifndef GUI - mprintf(St(MNotRAR),ArcName); -#endif - if (CmpExt(ArcName,"rar")) - ErrHandler.SetErrorCode(WARNING); - return(EXTRACT_ARC_NEXT); - } - - if (!Arc.IsOpened()) - return(EXTRACT_ARC_NEXT); - -#ifndef SFX_MODULE - if (Arc.Volume && Arc.NotFirstVolume) - { - char FirstVolName[NM]; - - VolNameToFirstName(ArcName,FirstVolName,(Arc.NewMhd.Flags & MHD_NEWNUMBERING)); - if (stricomp(ArcName,FirstVolName)!=0 && FileExist(FirstVolName) && - Cmd->ArcNames->Search(FirstVolName,NULL,false)) - return(EXTRACT_ARC_NEXT); - } -#endif - ExtractArchiveInit(Cmd,Arc); - - if (*Cmd->Command=='T' || *Cmd->Command=='I') - Cmd->Test=true; - -#ifndef GUI - if (*Cmd->Command=='I') - Cmd->DisablePercentage=true; - else - if (Cmd->Test) - mprintf(St(MExtrTest),ArcName); - else - mprintf(St(MExtracting),ArcName); -#endif - - Arc.ViewComment(); - - // RAR can close a corrupt encrypted archive - if (!Arc.IsOpened()) - return(EXTRACT_ARC_NEXT); - - - while (1) - { - int Size=Arc.ReadHeader(); - bool Repeat=false; - if (!ExtractCurrentFile(Cmd,Arc,Size,Repeat)) - if (Repeat) - { - return(EXTRACT_ARC_REPEAT); - } - else - break; - } - - return(EXTRACT_ARC_NEXT); -} - - -bool CmdExtract::ExtractCurrentFile(CommandData *Cmd,Archive &Arc,int HeaderSize,bool &Repeat) -{ - char Command=*Cmd->Command; - if (HeaderSize<=0) - if (DataIO.UnpVolume) - { -#ifdef NOVOLUME - return(false); -#else - if (!MergeArchive(Arc,NULL,false,Command)) - { - ErrHandler.SetErrorCode(WARNING); - return(false); - } - SignatureFound=false; -#endif - } - else - return(false); - int HeadType=Arc.GetHeaderType(); - if (HeadType!=FILE_HEAD) - { - if (HeadType==AV_HEAD || HeadType==SIGN_HEAD) - SignatureFound=true; -#if !defined(SFX_MODULE) && !defined(_WIN_CE) - if (HeadType==SUB_HEAD && PrevExtracted) - SetExtraInfo(Cmd,Arc,DestFileName,*DestFileNameW ? DestFileNameW:NULL); -#endif - if (HeadType==NEWSUB_HEAD) - { - if (Arc.SubHead.CmpName(SUBHEAD_TYPE_AV)) - SignatureFound=true; -#if !defined(NOSUBBLOCKS) && !defined(_WIN_CE) - if (PrevExtracted) - SetExtraInfoNew(Cmd,Arc,DestFileName,*DestFileNameW ? DestFileNameW:NULL); -#endif - } - if (HeadType==ENDARC_HEAD) - if (Arc.EndArcHead.Flags & EARC_NEXT_VOLUME) - { -#ifndef NOVOLUME - if (!MergeArchive(Arc,NULL,false,Command)) - { - ErrHandler.SetErrorCode(WARNING); - return(false); - } - SignatureFound=false; -#endif - Arc.Seek(Arc.CurBlockPos,SEEK_SET); - return(true); - } - else - return(false); - Arc.SeekToNext(); - return(true); - } - PrevExtracted=false; - - if (SignatureFound || - !Cmd->Recurse && MatchedArgs>=Cmd->FileArgs->ItemsCount() && - AllMatchesExact) - return(false); - - char ArcFileName[NM]; - IntToExt(Arc.NewLhd.FileName,Arc.NewLhd.FileName); - strcpy(ArcFileName,Arc.NewLhd.FileName); - - wchar ArcFileNameW[NM]; - *ArcFileNameW=0; - - int MatchType=MATCH_WILDSUBPATH; - - bool EqualNames=false; - int MatchNumber=Cmd->IsProcessFile(Arc.NewLhd,&EqualNames,MatchType); - bool ExactMatch=MatchNumber!=0; -#if !defined(SFX_MODULE) && !defined(_WIN_CE) - if (Cmd->ExclPath==EXCL_BASEPATH) - { - *Cmd->ArcPath=0; - if (ExactMatch) - { - Cmd->FileArgs->Rewind(); - if (Cmd->FileArgs->GetString(Cmd->ArcPath,NULL,sizeof(Cmd->ArcPath),MatchNumber-1)) - *PointToName(Cmd->ArcPath)=0; - } - } -#endif - if (ExactMatch && !EqualNames) - AllMatchesExact=false; - -#ifdef UNICODE_SUPPORTED - bool WideName=(Arc.NewLhd.Flags & LHD_UNICODE) && UnicodeEnabled(); -#else - bool WideName=false; -#endif - -#ifdef _APPLE - if (WideName) - { - WideToUtf(Arc.NewLhd.FileNameW,ArcFileName,sizeof(ArcFileName)); - WideName=false; - } -#endif - - wchar *DestNameW=WideName ? DestFileNameW:NULL; - -#ifdef UNICODE_SUPPORTED - if (WideName) - { - ConvertPath(Arc.NewLhd.FileNameW,ArcFileNameW); - char Name[NM]; - if (WideToChar(ArcFileNameW,Name) && IsNameUsable(Name)) - strcpy(ArcFileName,Name); - } -#endif - - ConvertPath(ArcFileName,ArcFileName); - - if (Arc.IsArcLabel()) - return(true); - - if (Arc.NewLhd.Flags & LHD_VERSION) - { - if (Cmd->VersionControl!=1 && !EqualNames) - { - if (Cmd->VersionControl==0) - ExactMatch=false; - int Version=ParseVersionFileName(ArcFileName,ArcFileNameW,false); - if (Cmd->VersionControl-1==Version) - ParseVersionFileName(ArcFileName,ArcFileNameW,true); - else - ExactMatch=false; - } - } - else - if (!Arc.IsArcDir() && Cmd->VersionControl>1) - ExactMatch=false; - - Arc.ConvertAttributes(); - -#ifndef SFX_MODULE - if ((Arc.NewLhd.Flags & (LHD_SPLIT_BEFORE/*|LHD_SOLID*/)) && FirstFile) - { - char CurVolName[NM]; - strcpy(CurVolName,ArcName); - - VolNameToFirstName(ArcName,ArcName,(Arc.NewMhd.Flags & MHD_NEWNUMBERING)); - if (stricomp(ArcName,CurVolName)!=0 && FileExist(ArcName)) - { - *ArcNameW=0; - Repeat=true; - return(false); - } -#if !defined(RARDLL) && !defined(_WIN_CE) - if (!ReconstructDone) - { - ReconstructDone=true; - - RecVolumes RecVol; - if (RecVol.Restore(Cmd,Arc.FileName,Arc.FileNameW,true)) - { - Repeat=true; - return(false); - } - } -#endif - strcpy(ArcName,CurVolName); - } -#endif - DataIO.UnpVolume=(Arc.NewLhd.Flags & LHD_SPLIT_AFTER); - DataIO.NextVolumeMissing=false; - - Arc.Seek(Arc.NextBlockPos-Arc.NewLhd.FullPackSize,SEEK_SET); - - bool TestMode=false; - bool ExtrFile=false; - bool SkipSolid=false; - -#ifndef SFX_MODULE - if (FirstFile && (ExactMatch || Arc.Solid) && (Arc.NewLhd.Flags & (LHD_SPLIT_BEFORE/*|LHD_SOLID*/))!=0) - { - if (ExactMatch) - { - Log(Arc.FileName,St(MUnpCannotMerge),ArcFileName); -#ifdef RARDLL - Cmd->DllError=ERAR_BAD_DATA; -#endif - ErrHandler.SetErrorCode(WARNING); - } - ExactMatch=false; - } - - FirstFile=false; -#endif - - if (ExactMatch || (SkipSolid=Arc.Solid)!=0) - { - if ((Arc.NewLhd.Flags & LHD_PASSWORD)!=0) -#ifndef RARDLL - if (*Password==0) -#endif - { -#ifdef RARDLL - if (*Cmd->Password==0) - if (Cmd->Callback==NULL || - Cmd->Callback(UCM_NEEDPASSWORD,Cmd->UserData,(LONG)Cmd->Password,sizeof(Cmd->Password))==-1) - return(false); - strcpy(Password,Cmd->Password); - -#else - if (!GetPassword(PASSWORD_FILE,ArcFileName,Password,sizeof(Password))) - { - PasswordCancelled=true; - return(false); - } -#endif - } -#if !defined(GUI) && !defined(SILENT) - else - if (!PasswordAll && (!Arc.Solid || Arc.NewLhd.UnpVer>=20 && (Arc.NewLhd.Flags & LHD_SOLID)==0)) - { - eprintf(St(MUseCurPsw),ArcFileName); - switch(Cmd->AllYes ? 1:Ask(St(MYesNoAll))) - { - case -1: - ErrHandler.Exit(USER_BREAK); - case 2: - if (!GetPassword(PASSWORD_FILE,ArcFileName,Password,sizeof(Password))) - { - return(false); - } - break; - case 3: - PasswordAll=true; - break; - } - } -#endif - -#ifndef SFX_MODULE - if (*Cmd->ExtrPath==0 && *Cmd->ExtrPathW!=0) - WideToChar(Cmd->ExtrPathW,DestFileName); - else -#endif - strcpy(DestFileName,Cmd->ExtrPath); - - -#ifndef SFX_MODULE - if (Cmd->AppendArcNameToPath) - { - strcat(DestFileName,PointToName(Arc.FirstVolumeName)); - SetExt(DestFileName,NULL); - AddEndSlash(DestFileName); - } -#endif - - char *ExtrName=ArcFileName; - - bool EmptyName=false; -#ifndef SFX_MODULE - int Length=strlen(Cmd->ArcPath); - if (Length>1 && IsPathDiv(Cmd->ArcPath[Length-1]) && - strlen(ArcFileName)==Length-1) - Length--; - if (Length>0 && strnicomp(Cmd->ArcPath,ArcFileName,Length)==0) - { - ExtrName+=Length; - while (*ExtrName==CPATHDIVIDER) - ExtrName++; - if (*ExtrName==0) - EmptyName=true; - } -#endif - - bool AbsPaths=Cmd->ExclPath==EXCL_ABSPATH && Command=='X' && IsDriveDiv(':'); - if (AbsPaths) - *DestFileName=0; - - if (Command=='E' || Cmd->ExclPath==EXCL_SKIPWHOLEPATH) - strcat(DestFileName,PointToName(ExtrName)); - else - strcat(DestFileName,ExtrName); - - char DiskLetter=etoupper(DestFileName[0]); - - if (AbsPaths && DestFileName[1]=='_' && IsPathDiv(DestFileName[2]) && - DiskLetter>='A' && DiskLetter<='Z') - DestFileName[1]=':'; - -#ifndef SFX_MODULE - if (!WideName && *Cmd->ExtrPathW!=0) - { - DestNameW=DestFileNameW; - WideName=true; - CharToWide(ArcFileName,ArcFileNameW); - } -#endif - - if (WideName) - { - if (*Cmd->ExtrPathW!=0) - strcpyw(DestFileNameW,Cmd->ExtrPathW); - else - CharToWide(Cmd->ExtrPath,DestFileNameW); - -#ifndef SFX_MODULE - if (Cmd->AppendArcNameToPath) - { - wchar FileNameW[NM]; - if (*Arc.FirstVolumeNameW!=0) - strcpyw(FileNameW,Arc.FirstVolumeNameW); - else - CharToWide(Arc.FirstVolumeName,FileNameW); - strcatw(DestFileNameW,PointToName(FileNameW)); - SetExt(DestFileNameW,NULL); - AddEndSlash(DestFileNameW); - } -#endif - wchar *ExtrNameW=ArcFileNameW; -#ifndef SFX_MODULE - if (Length>0) - { - wchar ArcPathW[NM]; - CharToWide(Cmd->ArcPath,ArcPathW); - Length=strlenw(ArcPathW); - } - ExtrNameW+=Length; - while (*ExtrNameW==CPATHDIVIDER) - ExtrNameW++; -#endif - - if (AbsPaths) - *DestFileNameW=0; - - if (Command=='E' || Cmd->ExclPath==EXCL_SKIPWHOLEPATH) - strcatw(DestFileNameW,PointToName(ExtrNameW)); - else - strcatw(DestFileNameW,ExtrNameW); - - if (AbsPaths && DestFileNameW[1]=='_' && IsPathDiv(DestFileNameW[2])) - DestFileNameW[1]=':'; - } - else - *DestFileNameW=0; - - ExtrFile=!SkipSolid && !EmptyName && (Arc.NewLhd.Flags & LHD_SPLIT_BEFORE)==0; - - if ((Cmd->FreshFiles || Cmd->UpdateFiles) && (Command=='E' || Command=='X')) - { - struct FindData FD; - if (FindFile::FastFind(DestFileName,DestNameW,&FD)) - { - if (FD.mtime >= Arc.NewLhd.mtime) - ExtrFile=false; - } - else - if (Cmd->FreshFiles) - ExtrFile=false; - } - - // skip encrypted file if no password is specified - if ((Arc.NewLhd.Flags & LHD_PASSWORD)!=0 && *Password==0) - { - ErrHandler.SetErrorCode(WARNING); -#ifdef RARDLL - Cmd->DllError=ERAR_MISSING_PASSWORD; -#endif - ExtrFile=false; - } - -#ifdef RARDLL - if (*Cmd->DllDestName) - { - strncpyz(DestFileName,Cmd->DllDestName,ASIZE(DestFileName)); - *DestFileNameW=0; - if (Cmd->DllOpMode!=RAR_EXTRACT) - ExtrFile=false; - } - if (*Cmd->DllDestNameW) - { - strncpyzw(DestFileNameW,Cmd->DllDestNameW,ASIZE(DestFileNameW)); - DestNameW=DestFileNameW; - if (Cmd->DllOpMode!=RAR_EXTRACT) - ExtrFile=false; - } -#endif - -#ifdef SFX_MODULE - if ((Arc.NewLhd.UnpVer!=UNP_VER && Arc.NewLhd.UnpVer!=29) && - Arc.NewLhd.Method!=0x30) -#else - if (Arc.NewLhd.UnpVer<13 || Arc.NewLhd.UnpVer>UNP_VER) -#endif - { -#ifndef SILENT - Log(Arc.FileName,St(MUnknownMeth),ArcFileName); -#ifndef SFX_MODULE - Log(Arc.FileName,St(MVerRequired),Arc.NewLhd.UnpVer/10,Arc.NewLhd.UnpVer%10); -#endif -#endif - ExtrFile=false; - ErrHandler.SetErrorCode(WARNING); -#ifdef RARDLL - Cmd->DllError=ERAR_UNKNOWN_FORMAT; -#endif - } - - File CurFile; - - if (!IsLink(Arc.NewLhd.FileAttr)) - if (Arc.IsArcDir()) - { - if (!ExtrFile || Command=='P' || Command=='E' || Cmd->ExclPath==EXCL_SKIPWHOLEPATH) - return(true); - if (SkipSolid) - { -#ifndef GUI - mprintf(St(MExtrSkipFile),ArcFileName); -#endif - return(true); - } - TotalFileCount++; - if (Cmd->Test) - { -#ifndef GUI - mprintf(St(MExtrTestFile),ArcFileName); - mprintf(" %s",St(MOk)); -#endif - return(true); - } - MKDIR_CODE MDCode=MakeDir(DestFileName,DestNameW,Arc.NewLhd.FileAttr); - bool DirExist=false; - if (MDCode!=MKDIR_SUCCESS) - { - DirExist=FileExist(DestFileName,DestNameW); - if (DirExist && !IsDir(GetFileAttr(DestFileName,DestNameW))) - { - bool UserReject; - FileCreate(Cmd,NULL,DestFileName,DestNameW,Cmd->Overwrite,&UserReject,Arc.NewLhd.FullUnpSize,Arc.NewLhd.FileTime); - DirExist=false; - } - CreatePath(DestFileName,DestNameW,true); - MDCode=MakeDir(DestFileName,DestNameW,Arc.NewLhd.FileAttr); - } - if (MDCode==MKDIR_SUCCESS) - { -#ifndef GUI - mprintf(St(MCreatDir),DestFileName); - mprintf(" %s",St(MOk)); -#endif - PrevExtracted=true; - } - else - if (DirExist) - { - SetFileAttr(DestFileName,DestNameW,Arc.NewLhd.FileAttr); - PrevExtracted=true; - } - else - { - Log(Arc.FileName,St(MExtrErrMkDir),DestFileName); - ErrHandler.SysErrMsg(); -#ifdef RARDLL - Cmd->DllError=ERAR_ECREATE; -#endif - ErrHandler.SetErrorCode(CREATE_ERROR); - } - if (PrevExtracted) - { -#if defined(_WIN_32) && !defined(_WIN_CE) && !defined(SFX_MODULE) - if (Cmd->SetCompressedAttr && - (Arc.NewLhd.FileAttr & FILE_ATTRIBUTE_COMPRESSED)!=0 && WinNT()) - SetFileCompression(DestFileName,DestFileNameW,true); -#endif - SetDirTime(DestFileName, - Cmd->xmtime==EXTTIME_NONE ? NULL:&Arc.NewLhd.mtime, - Cmd->xctime==EXTTIME_NONE ? NULL:&Arc.NewLhd.ctime, - Cmd->xatime==EXTTIME_NONE ? NULL:&Arc.NewLhd.atime); - } - return(true); - } - else - { - if (Cmd->Test && ExtrFile) - TestMode=true; -#if !defined(GUI) && !defined(SFX_MODULE) - if (Command=='P' && ExtrFile) - CurFile.SetHandleType(FILE_HANDLESTD); -#endif - if ((Command=='E' || Command=='X') && ExtrFile && !Cmd->Test) - { - bool UserReject; - if (!FileCreate(Cmd,&CurFile,DestFileName,DestNameW,Cmd->Overwrite,&UserReject,Arc.NewLhd.FullUnpSize,Arc.NewLhd.FileTime)) - { - ExtrFile=false; - if (!UserReject) - { - ErrHandler.CreateErrorMsg(Arc.FileName,DestFileName); - ErrHandler.SetErrorCode(CREATE_ERROR); -#ifdef RARDLL - Cmd->DllError=ERAR_ECREATE; -#endif - if (!IsNameUsable(DestFileName)) - { - Log(Arc.FileName,St(MCorrectingName)); - char OrigName[sizeof(DestFileName)]; - strncpyz(OrigName,DestFileName,ASIZE(OrigName)); - - MakeNameUsable(DestFileName,true); - CreatePath(DestFileName,NULL,true); - if (FileCreate(Cmd,&CurFile,DestFileName,NULL,Cmd->Overwrite,&UserReject,Arc.NewLhd.FullUnpSize,Arc.NewLhd.FileTime)) - { -#ifndef SFX_MODULE - Log(Arc.FileName,St(MRenaming),OrigName,DestFileName); -#endif - ExtrFile=true; - } - else - ErrHandler.CreateErrorMsg(Arc.FileName,DestFileName); - } - } - } - } - } - - if (!ExtrFile && Arc.Solid) - { - SkipSolid=true; - TestMode=true; - ExtrFile=true; - } - if (ExtrFile) - { - if (!SkipSolid) - { - if (!TestMode && Command!='P' && CurFile.IsDevice()) - { - Log(Arc.FileName,St(MInvalidName),DestFileName); - ErrHandler.WriteError(Arc.FileName,DestFileName); - } - TotalFileCount++; - } - FileCount++; -#ifndef GUI - if (Command!='I') - if (SkipSolid) - mprintf(St(MExtrSkipFile),ArcFileName); - else - switch(Cmd->Test ? 'T':Command) - { - case 'T': - mprintf(St(MExtrTestFile),ArcFileName); - break; -#ifndef SFX_MODULE - case 'P': - mprintf(St(MExtrPrinting),ArcFileName); - break; -#endif - case 'X': - case 'E': - mprintf(St(MExtrFile),DestFileName); - break; - } - if (!Cmd->DisablePercentage) - mprintf(" "); -#endif - DataIO.CurUnpRead=0; - DataIO.CurUnpWrite=0; - DataIO.UnpFileCRC=Arc.OldFormat ? 0 : 0xffffffff; - DataIO.PackedCRC=0xffffffff; - DataIO.SetEncryption( - (Arc.NewLhd.Flags & LHD_PASSWORD) ? Arc.NewLhd.UnpVer:0,Password, - (Arc.NewLhd.Flags & LHD_SALT) ? Arc.NewLhd.Salt:NULL,false, - Arc.NewLhd.UnpVer>=36); - DataIO.SetPackedSizeToRead(Arc.NewLhd.FullPackSize); - DataIO.SetFiles(&Arc,&CurFile); - DataIO.SetTestMode(TestMode); - DataIO.SetSkipUnpCRC(SkipSolid); -#ifndef _WIN_CE - if (!TestMode && !Arc.BrokenFileHeader && - (Arc.NewLhd.FullPackSize<<11)>Arc.NewLhd.FullUnpSize && - (Arc.NewLhd.FullUnpSize<100000000 || Arc.FileLength()>Arc.NewLhd.FullPackSize)) - CurFile.Prealloc(Arc.NewLhd.FullUnpSize); -#endif - - CurFile.SetAllowDelete(!Cmd->KeepBroken); - - bool LinkCreateMode=!Cmd->Test && !SkipSolid; - if (ExtractLink(DataIO,Arc,DestFileName,DataIO.UnpFileCRC,LinkCreateMode)) - PrevExtracted=LinkCreateMode; - else - if ((Arc.NewLhd.Flags & LHD_SPLIT_BEFORE)==0) - if (Arc.NewLhd.Method==0x30) - UnstoreFile(DataIO,Arc.NewLhd.FullUnpSize); - else - { - Unp->SetDestSize(Arc.NewLhd.FullUnpSize); -#ifndef SFX_MODULE - if (Arc.NewLhd.UnpVer<=15) - Unp->DoUnpack(15,FileCount>1 && Arc.Solid); - else -#endif - Unp->DoUnpack(Arc.NewLhd.UnpVer,Arc.NewLhd.Flags & LHD_SOLID); - } - - if (Arc.IsOpened()) - Arc.SeekToNext(); - - bool BrokenFile=false; - if (!SkipSolid) - { - if (Arc.OldFormat && UINT32(DataIO.UnpFileCRC)==UINT32(Arc.NewLhd.FileCRC) || - !Arc.OldFormat && UINT32(DataIO.UnpFileCRC)==UINT32(Arc.NewLhd.FileCRC^0xffffffff)) - { -#ifndef GUI - if (Command!='P' && Command!='I') - mprintf("%s%s ",Cmd->DisablePercentage ? " ":"\b\b\b\b\b ",St(MOk)); -#endif - } - else - { - char *BadArcName=/*(Arc.NewLhd.Flags & LHD_SPLIT_BEFORE) ? NULL:*/Arc.FileName; - if (Arc.NewLhd.Flags & LHD_PASSWORD) - { - Log(BadArcName,St(MEncrBadCRC),ArcFileName); - } - else - { - Log(BadArcName,St(MCRCFailed),ArcFileName); - } - BrokenFile=true; - ErrHandler.SetErrorCode(CRC_ERROR); -#ifdef RARDLL - Cmd->DllError=ERAR_BAD_DATA; -#endif - Alarm(); - } - } -#ifndef GUI - else - mprintf("\b\b\b\b\b "); -#endif - - if (!TestMode && (Command=='X' || Command=='E') && - !IsLink(Arc.NewLhd.FileAttr)) - { -#if defined(_WIN_32) || defined(_EMX) - if (Cmd->ClearArc) - Arc.NewLhd.FileAttr&=~FA_ARCH; -/* - else - Arc.NewLhd.FileAttr|=FA_ARCH; //set archive bit for unpacked files (file is not backed up) -*/ -#endif - if (!BrokenFile || Cmd->KeepBroken) - { - if (BrokenFile) - CurFile.Truncate(); - CurFile.SetOpenFileStat( - Cmd->xmtime==EXTTIME_NONE ? NULL:&Arc.NewLhd.mtime, - Cmd->xctime==EXTTIME_NONE ? NULL:&Arc.NewLhd.ctime, - Cmd->xatime==EXTTIME_NONE ? NULL:&Arc.NewLhd.atime); - CurFile.Close(); -#if defined(_WIN_32) && !defined(_WIN_CE) && !defined(SFX_MODULE) - if (Cmd->SetCompressedAttr && - (Arc.NewLhd.FileAttr & FILE_ATTRIBUTE_COMPRESSED)!=0 && WinNT()) - SetFileCompression(CurFile.FileName,CurFile.FileNameW,true); -#endif - CurFile.SetCloseFileStat( - Cmd->xmtime==EXTTIME_NONE ? NULL:&Arc.NewLhd.mtime, - Cmd->xatime==EXTTIME_NONE ? NULL:&Arc.NewLhd.atime, - Arc.NewLhd.FileAttr); - PrevExtracted=true; - } - } - } - } - if (ExactMatch) - MatchedArgs++; - if (DataIO.NextVolumeMissing || !Arc.IsOpened()) - return(false); - if (!ExtrFile) - if (!Arc.Solid) - Arc.SeekToNext(); - else - if (!SkipSolid) - return(false); - return(true); -} - - -void CmdExtract::UnstoreFile(ComprDataIO &DataIO,Int64 DestUnpSize) -{ - Array Buffer(0x10000); - while (1) - { - unsigned int Code=DataIO.UnpRead(&Buffer[0],Buffer.Size()); - if (Code==0 || (int)Code==-1) - break; - Code=Code=0) - DestUnpSize-=Code; - } -} - diff --git a/src/bin/unrar/extract.hpp b/src/bin/unrar/extract.hpp deleted file mode 100644 index 09dfc94f8f..0000000000 --- a/src/bin/unrar/extract.hpp +++ /dev/null @@ -1,42 +0,0 @@ -#ifndef _RAR_EXTRACT_ -#define _RAR_EXTRACT_ - -enum EXTRACT_ARC_CODE {EXTRACT_ARC_NEXT,EXTRACT_ARC_REPEAT}; - -class CmdExtract -{ - private: - EXTRACT_ARC_CODE ExtractArchive(CommandData *Cmd); - - ComprDataIO DataIO; - Unpack *Unp; - long TotalFileCount; - - long FileCount; - long MatchedArgs; - bool FirstFile; - bool AllMatchesExact; - bool ReconstructDone; - - char ArcName[NM]; - wchar ArcNameW[NM]; - - char Password[MAXPASSWORD]; - bool PasswordAll; - bool PrevExtracted; - char DestFileName[NM]; - wchar DestFileNameW[NM]; - bool PasswordCancelled; - public: - CmdExtract(); - ~CmdExtract(); - void DoExtract(CommandData *Cmd); - void ExtractArchiveInit(CommandData *Cmd,Archive &Arc); - bool ExtractCurrentFile(CommandData *Cmd,Archive &Arc,int HeaderSize, - bool &Repeat); - static void UnstoreFile(ComprDataIO &DataIO,Int64 DestUnpSize); - - bool SignatureFound; -}; - -#endif diff --git a/src/bin/unrar/filcreat.cpp b/src/bin/unrar/filcreat.cpp deleted file mode 100644 index 175736a663..0000000000 --- a/src/bin/unrar/filcreat.cpp +++ /dev/null @@ -1,239 +0,0 @@ -#include "rar.hpp" - -bool FileCreate(RAROptions *Cmd,File *NewFile,char *Name,wchar *NameW, - OVERWRITE_MODE Mode,bool *UserReject,Int64 FileSize, - uint FileTime) -{ - if (UserReject!=NULL) - *UserReject=false; -#if defined(_WIN_32) && !defined(_WIN_CE) - bool ShortNameChanged=false; -#endif - while (FileExist(Name,NameW)) - { -#if defined(_WIN_32) && !defined(_WIN_CE) - if (!ShortNameChanged) - { - ShortNameChanged=true; - if (UpdateExistingShortName(Name,NameW)) - continue; - } -#endif - if (Mode==OVERWRITE_NONE) - { - if (UserReject!=NULL) - *UserReject=true; - return(false); - } -#ifdef SILENT - Mode=OVERWRITE_ALL; -#endif - if (Cmd->AllYes || Mode==OVERWRITE_ALL) - break; - if (Mode==OVERWRITE_ASK) - { - eprintf(St(MFileExists),Name); - int Choice=Ask(St(MYesNoAllRenQ)); - if (Choice==1) - break; - if (Choice==2) - { - if (UserReject!=NULL) - *UserReject=true; - return(false); - } - if (Choice==3) - { - Cmd->Overwrite=OVERWRITE_ALL; - break; - } - if (Choice==4) - { - if (UserReject!=NULL) - *UserReject=true; - Cmd->Overwrite=OVERWRITE_NONE; - return(false); - } - if (Choice==5) - { - mprintf(St(MAskNewName)); - - char NewName[NM]; -#ifdef _WIN_32 - File SrcFile; - SrcFile.SetHandleType(FILE_HANDLESTD); - int Size=SrcFile.Read(NewName,sizeof(NewName)-1); - NewName[Size]=0; - OemToChar(NewName,NewName); -#else - fgets(NewName,sizeof(NewName),stdin); -#endif - RemoveLF(NewName); - if (PointToName(NewName)==NewName) - strcpy(PointToName(Name),NewName); - else - strcpy(Name,NewName); - if (NameW!=NULL) - *NameW=0; - continue; - } - if (Choice==6) - ErrHandler.Exit(USER_BREAK); - } - if (Mode==OVERWRITE_AUTORENAME) - { - if (GetAutoRenamedName(Name)) - { - if (NameW!=NULL) - *NameW=0; - } - else - Mode=OVERWRITE_ASK; - continue; - } - } - if (NewFile!=NULL && NewFile->Create(Name,NameW)) - return(true); - PrepareToDelete(Name,NameW); - CreatePath(Name,NameW,true); - return(NewFile!=NULL ? NewFile->Create(Name,NameW):DelFile(Name,NameW)); -} - - -bool GetAutoRenamedName(char *Name) -{ - char NewName[NM]; - - if (strlen(Name)>sizeof(NewName)-10) - return(false); - char *Ext=GetExt(Name); - if (Ext==NULL) - Ext=Name+strlen(Name); - for (int FileVer=1;;FileVer++) - { - sprintf(NewName,"%.*s(%d)%s",Ext-Name,Name,FileVer,Ext); - if (!FileExist(NewName)) - { - strcpy(Name,NewName); - break; - } - if (FileVer>=1000000) - return(false); - } - return(true); -} - - -#if defined(_WIN_32) && !defined(_WIN_CE) -bool UpdateExistingShortName(char *Name,wchar *NameW) -{ - FindData fd; - if (!FindFile::FastFind(Name,NameW,&fd)) - return(false); - if (*fd.Name==0 || *fd.ShortName==0) - return(false); - if (stricomp(PointToName(fd.Name),fd.ShortName)==0 || - stricomp(PointToName(Name),fd.ShortName)!=0) - return(false); - - char NewName[NM]; - for (int I=0;I<10000;I+=123) - { - strncpyz(NewName,Name,ASIZE(NewName)); - sprintf(PointToName(NewName),"rtmp%d",I); - if (!FileExist(NewName)) - break; - } - if (FileExist(NewName)) - return(false); - char FullName[NM]; - strncpyz(FullName,Name,ASIZE(FullName)); - strcpy(PointToName(FullName),PointToName(fd.Name)); - if (!MoveFile(FullName,NewName)) - return(false); - File KeepShortFile; - bool Created=false; - if (!FileExist(Name)) - Created=KeepShortFile.Create(Name); - MoveFile(NewName,FullName); - if (Created) - { - KeepShortFile.Close(); - KeepShortFile.Delete(); - } - return(true); -} - -/* -bool UpdateExistingShortName(char *Name,wchar *NameW) -{ - if (WinNT()<5) - return(false); - FindData fd; - if (!FindFile::FastFind(Name,NameW,&fd)) - return(false); - if (*fd.Name==0 || *fd.ShortName==0) - return(false); - if (stricomp(PointToName(fd.Name),fd.ShortName)==0 || - stricomp(PointToName(Name),fd.ShortName)!=0) - return(false); - - typedef BOOL (WINAPI *SETFILESHORTNAME)(HANDLE,LPCSTR); - static SETFILESHORTNAME pSetFileShortName=NULL; - if (pSetFileShortName==NULL) - { - HMODULE hKernel=GetModuleHandle("kernel32.dll"); - if (hKernel!=NULL) - pSetFileShortName=(SETFILESHORTNAME)GetProcAddress(hKernel,"SetFileShortNameA"); - if (pSetFileShortName==NULL) - return(false); - } - static bool RestoreEnabled=false; - if (!RestoreEnabled) - { - HANDLE hToken; - if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &hToken)) - return(false); - - TOKEN_PRIVILEGES tp; - tp.PrivilegeCount = 1; - tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED; - - if (LookupPrivilegeValue(NULL,SE_RESTORE_NAME,&tp.Privileges[0].Luid)) - AdjustTokenPrivileges(hToken, FALSE, &tp, 0, NULL, NULL); - - CloseHandle(hToken); - RestoreEnabled=true; - } - - wchar FileNameW[NM]; - GetWideName(Name,NameW,FileNameW); - HANDLE hFile=CreateFileW(FileNameW,GENERIC_WRITE|DELETE,FILE_SHARE_READ|FILE_SHARE_WRITE, - NULL,OPEN_EXISTING,FILE_FLAG_BACKUP_SEMANTICS,NULL); - if (hFile==INVALID_HANDLE_VALUE) - return(false); - - bool RetCode=false; - - char FullName[NM]; - wchar FullNameW[NM]; - strcpy(FullName,Name); - strcpyw(FullNameW,NullToEmpty(NameW)); - for (int I=1;I<1000000;I++) - { - char NewName[NM]; - sprintf(NewName,"NAME~%d.%d",I%1000,I/1000+1); - strcpy(PointToName(FullName),NewName); - if (*FullNameW) - CharToWide(NewName,PointToName(FullNameW)); - if (!FileExist(FullName,FullNameW)) - { - RetCode=pSetFileShortName(hFile,NewName); - break; - } - } - CloseHandle(hFile); - return(RetCode); -} -*/ -#endif diff --git a/src/bin/unrar/filcreat.hpp b/src/bin/unrar/filcreat.hpp deleted file mode 100644 index d803582a1a..0000000000 --- a/src/bin/unrar/filcreat.hpp +++ /dev/null @@ -1,13 +0,0 @@ -#ifndef _RAR_FILECREATE_ -#define _RAR_FILECREATE_ - -bool FileCreate(RAROptions *Cmd,File *NewFile,char *Name,wchar *NameW, - OVERWRITE_MODE Mode,bool *UserReject,Int64 FileSize=INT64ERR, - uint FileTime=0); -bool GetAutoRenamedName(char *Name); - -#if defined(_WIN_32) && !defined(_WIN_CE) -bool UpdateExistingShortName(char *Name,wchar *NameW); -#endif - -#endif diff --git a/src/bin/unrar/file.cpp b/src/bin/unrar/file.cpp deleted file mode 100644 index f8dba45d2b..0000000000 --- a/src/bin/unrar/file.cpp +++ /dev/null @@ -1,704 +0,0 @@ -#include "rar.hpp" - -static File *CreatedFiles[256]; -static int RemoveCreatedActive=0; - -File::File() -{ - hFile=BAD_HANDLE; - *FileName=0; - *FileNameW=0; - NewFile=false; - LastWrite=false; - HandleType=FILE_HANDLENORMAL; - SkipClose=false; - IgnoreReadErrors=false; - ErrorType=FILE_SUCCESS; - OpenShared=false; - AllowDelete=true; - CloseCount=0; - AllowExceptions=true; -#ifdef _WIN_32 - NoSequentialRead=false; -#endif -} - - -File::~File() -{ - if (hFile!=BAD_HANDLE && !SkipClose) - if (NewFile) - Delete(); - else - Close(); -} - - -void File::operator = (File &SrcFile) -{ - hFile=SrcFile.hFile; - strcpy(FileName,SrcFile.FileName); - NewFile=SrcFile.NewFile; - LastWrite=SrcFile.LastWrite; - HandleType=SrcFile.HandleType; - SrcFile.SkipClose=true; -} - - -bool File::Open(const char *Name,const wchar *NameW,bool OpenShared,bool Update) -{ - ErrorType=FILE_SUCCESS; - FileHandle hNewFile; - if (File::OpenShared) - OpenShared=true; -#ifdef _WIN_32 - uint Access=GENERIC_READ; - if (Update) - Access|=GENERIC_WRITE; - uint ShareMode=FILE_SHARE_READ; - if (OpenShared) - ShareMode|=FILE_SHARE_WRITE; - uint Flags=NoSequentialRead ? 0:FILE_FLAG_SEQUENTIAL_SCAN; - if (WinNT() && NameW!=NULL && *NameW!=0) - hNewFile=CreateFileW(NameW,Access,ShareMode,NULL,OPEN_EXISTING,Flags,NULL); - else - hNewFile=CreateFile(Name,Access,ShareMode,NULL,OPEN_EXISTING,Flags,NULL); - - if (hNewFile==BAD_HANDLE && GetLastError()==ERROR_FILE_NOT_FOUND) - ErrorType=FILE_NOTFOUND; -#else - int flags=Update ? O_RDWR:O_RDONLY; -#ifdef O_BINARY - flags|=O_BINARY; -#if defined(_AIX) && defined(_LARGE_FILE_API) - flags|=O_LARGEFILE; -#endif -#endif -#if defined(_EMX) && !defined(_DJGPP) - int sflags=OpenShared ? SH_DENYNO:SH_DENYWR; - int handle=sopen(Name,flags,sflags); -#else - int handle=open(Name,flags); -#ifdef LOCK_EX - -#ifdef _OSF_SOURCE - extern "C" int flock(int, int); -#endif - -#ifndef __HAIKU__ - if (!OpenShared && Update && handle>=0 && flock(handle,LOCK_EX|LOCK_NB)==-1) - { - close(handle); - return(false); - } -#else - { - struct flock lock; - lock.l_type=LOCK_EX|LOCK_NB; - lock.l_whence=SEEK_SET; - lock.l_start=0; - lock.l_len=OFF_MAX; - if (!OpenShared && Update && handle>=0 && fcntl(handle,F_SETLK,&lock)==-1) - { - close(handle); - return(false); - } - } -#endif -#endif -#endif - hNewFile=handle==-1 ? BAD_HANDLE:fdopen(handle,Update ? UPDATEBINARY:READBINARY); - if (hNewFile==BAD_HANDLE && errno==ENOENT) - ErrorType=FILE_NOTFOUND; -#endif - NewFile=false; - HandleType=FILE_HANDLENORMAL; - SkipClose=false; - bool Success=hNewFile!=BAD_HANDLE; - if (Success) - { - hFile=hNewFile; - if (NameW!=NULL) - strcpyw(FileNameW,NameW); - else - *FileNameW=0; - if (Name!=NULL) - strcpy(FileName,Name); - else - WideToChar(NameW,FileName); - AddFileToList(hFile); - } - return(Success); -} - - -#if !defined(SHELL_EXT) && !defined(SFX_MODULE) -void File::TOpen(const char *Name,const wchar *NameW) -{ - if (!WOpen(Name,NameW)) - ErrHandler.Exit(OPEN_ERROR); -} -#endif - - -bool File::WOpen(const char *Name,const wchar *NameW) -{ - if (Open(Name,NameW)) - return(true); - ErrHandler.OpenErrorMsg(Name); - return(false); -} - - -bool File::Create(const char *Name,const wchar *NameW) -{ -#ifdef _WIN_32 - if (WinNT() && NameW!=NULL && *NameW!=0) - hFile=CreateFileW(NameW,GENERIC_READ|GENERIC_WRITE,FILE_SHARE_READ,NULL, - CREATE_ALWAYS,0,NULL); - else - hFile=CreateFile(Name,GENERIC_READ|GENERIC_WRITE,FILE_SHARE_READ,NULL, - CREATE_ALWAYS,0,NULL); -#else - hFile=fopen(Name,CREATEBINARY); -#endif - NewFile=true; - HandleType=FILE_HANDLENORMAL; - SkipClose=false; - if (NameW!=NULL) - strcpyw(FileNameW,NameW); - else - *FileNameW=0; - if (Name!=NULL) - strcpy(FileName,Name); - else - WideToChar(NameW,FileName); - AddFileToList(hFile); - return(hFile!=BAD_HANDLE); -} - - -void File::AddFileToList(FileHandle hFile) -{ - if (hFile!=BAD_HANDLE) - for (int I=0;ISize && FilePos-Size<=0xffffffff && FilePos+Size>0xffffffff) - ErrHandler.WriteErrorFAT(FileName); -#endif - if (ErrHandler.AskRepeatWrite(FileName)) - { -#ifndef _WIN_32 - clearerr(hFile); -#endif - if (Written0) - Seek(Tell()-Written,SEEK_SET); - continue; - } - ErrHandler.WriteError(NULL,FileName); - } - break; - } - LastWrite=true; -} - - -int File::Read(void *Data,int Size) -{ - Int64 FilePos; - if (IgnoreReadErrors) - FilePos=Tell(); - int ReadSize; - while (true) - { - ReadSize=DirectRead(Data,Size); - if (ReadSize==-1) - { - ErrorType=FILE_READERROR; - if (AllowExceptions) - if (IgnoreReadErrors) - { - ReadSize=0; - for (int I=0;IMaxDeviceRead) - Size=MaxDeviceRead; - hFile=GetStdHandle(STD_INPUT_HANDLE); -#else - hFile=stdin; -#endif - } -#endif -#ifdef _WIN_32 - DWORD Read; - if (!ReadFile(hFile,Data,Size,&Read,NULL)) - { - if (IsDevice() && Size>MaxDeviceRead) - return(DirectRead(Data,MaxDeviceRead)); - if (HandleType==FILE_HANDLESTD && GetLastError()==ERROR_BROKEN_PIPE) - return(0); - return(-1); - } - return(Read); -#else - if (LastWrite) - { - fflush(hFile); - LastWrite=false; - } - clearerr(hFile); - int ReadSize=fread(Data,1,Size,hFile); - if (ferror(hFile)) - return(-1); - return(ReadSize); -#endif -} - - -void File::Seek(Int64 Offset,int Method) -{ - if (!RawSeek(Offset,Method) && AllowExceptions) - ErrHandler.SeekError(FileName); -} - - -bool File::RawSeek(Int64 Offset,int Method) -{ - if (hFile==BAD_HANDLE) - return(true); - if (!is64plus(Offset) && Method!=SEEK_SET) - { - Offset=(Method==SEEK_CUR ? Tell():FileLength())+Offset; - Method=SEEK_SET; - } -#ifdef _WIN_32 - LONG HighDist=int64to32(Offset>>32); - if (SetFilePointer(hFile,int64to32(Offset),&HighDist,Method)==0xffffffff && - GetLastError()!=NO_ERROR) - return(false); -#else - LastWrite=false; -#if defined(_LARGEFILE_SOURCE) && !defined(_OSF_SOURCE) && !defined(__VMS) - if (fseeko(hFile,Offset,Method)!=0) -#else - if (fseek(hFile,(long)int64to32(Offset),Method)!=0) -#endif - return(false); -#endif - return(true); -} - - -Int64 File::Tell() -{ -#ifdef _WIN_32 - LONG HighDist=0; - uint LowDist=SetFilePointer(hFile,0,&HighDist,FILE_CURRENT); - if (LowDist==0xffffffff && GetLastError()!=NO_ERROR) - if (AllowExceptions) - ErrHandler.SeekError(FileName); - else - return(-1); - return(int32to64(HighDist,LowDist)); -#else -#if defined(_LARGEFILE_SOURCE) && !defined(_OSF_SOURCE) - return(ftello(hFile)); -#else - return(ftell(hFile)); -#endif -#endif -} - - -void File::Prealloc(Int64 Size) -{ -#ifdef _WIN_32 - if (RawSeek(Size,SEEK_SET)) - { - Truncate(); - Seek(0,SEEK_SET); - } -#endif -} - - -byte File::GetByte() -{ - byte Byte=0; - Read(&Byte,1); - return(Byte); -} - - -void File::PutByte(byte Byte) -{ - Write(&Byte,1); -} - - -bool File::Truncate() -{ -#ifdef _WIN_32 - return(SetEndOfFile(hFile)); -#else - return(false); -#endif -} - - -void File::SetOpenFileTime(RarTime *ftm,RarTime *ftc,RarTime *fta) -{ -#ifdef _WIN_32 - bool sm=ftm!=NULL && ftm->IsSet(); - bool sc=ftc!=NULL && ftc->IsSet(); - bool sa=fta!=NULL && fta->IsSet(); - FILETIME fm,fc,fa; - if (sm) - ftm->GetWin32(&fm); - if (sc) - ftc->GetWin32(&fc); - if (sa) - fta->GetWin32(&fa); - SetFileTime(hFile,sc ? &fc:NULL,sa ? &fa:NULL,sm ? &fm:NULL); -#endif -} - - -void File::SetCloseFileTime(RarTime *ftm,RarTime *fta) -{ -#if defined(_UNIX) || defined(_EMX) - SetCloseFileTimeByName(FileName,ftm,fta); -#endif -} - - -void File::SetCloseFileTimeByName(const char *Name,RarTime *ftm,RarTime *fta) -{ -#if defined(_UNIX) || defined(_EMX) - bool setm=ftm!=NULL && ftm->IsSet(); - bool seta=fta!=NULL && fta->IsSet(); - if (setm || seta) - { - struct utimbuf ut; - if (setm) - ut.modtime=ftm->GetUnix(); - else - ut.modtime=fta->GetUnix(); - if (seta) - ut.actime=fta->GetUnix(); - else - ut.actime=ut.modtime; - utime(Name,&ut); - } -#endif -} - - -void File::GetOpenFileTime(RarTime *ft) -{ -#ifdef _WIN_32 - FILETIME FileTime; - GetFileTime(hFile,NULL,NULL,&FileTime); - *ft=FileTime; -#endif -#if defined(_UNIX) || defined(_EMX) - struct stat st; - fstat(fileno(hFile),&st); - *ft=st.st_mtime; -#endif -} - - -void File::SetOpenFileStat(RarTime *ftm,RarTime *ftc,RarTime *fta) -{ -#ifdef _WIN_32 - SetOpenFileTime(ftm,ftc,fta); -#endif -} - - -void File::SetCloseFileStat(RarTime *ftm,RarTime *fta,uint FileAttr) -{ -#ifdef _WIN_32 - SetFileAttr(FileName,FileNameW,FileAttr); -#endif -#ifdef _EMX - SetCloseFileTime(ftm,fta); - SetFileAttr(FileName,FileNameW,FileAttr); -#endif -#ifdef _UNIX - SetCloseFileTime(ftm,fta); - chmod(FileName,(mode_t)FileAttr); -#endif -} - - -Int64 File::FileLength() -{ - SaveFilePos SavePos(*this); - Seek(0,SEEK_END); - return(Tell()); -} - - -void File::SetHandleType(FILE_HANDLETYPE Type) -{ - HandleType=Type; -} - - -bool File::IsDevice() -{ - if (hFile==BAD_HANDLE) - return(false); -#ifdef _WIN_32 - uint Type=GetFileType(hFile); - return(Type==FILE_TYPE_CHAR || Type==FILE_TYPE_PIPE); -#else - return(isatty(fileno(hFile))); -#endif -} - - -#ifndef SFX_MODULE -void File::fprintf(const char *fmt,...) -{ - va_list argptr; - va_start(argptr,fmt); - safebuf char Msg[2*NM+1024],OutMsg[2*NM+1024]; - vsprintf(Msg,fmt,argptr); -#ifdef _WIN_32 - for (int Src=0,Dest=0;;Src++) - { - char CurChar=Msg[Src]; - if (CurChar=='\n') - OutMsg[Dest++]='\r'; - OutMsg[Dest++]=CurChar; - if (CurChar==0) - break; - } -#else - strcpy(OutMsg,Msg); -#endif - Write(OutMsg,strlen(OutMsg)); - va_end(argptr); -} -#endif - - -bool File::RemoveCreated() -{ - RemoveCreatedActive++; - bool RetCode=true; - for (int I=0;ISetExceptions(false); - bool Success; - if (CreatedFiles[I]->NewFile) - Success=CreatedFiles[I]->Delete(); - else - Success=CreatedFiles[I]->Close(); - if (Success) - CreatedFiles[I]=NULL; - else - RetCode=false; - } - RemoveCreatedActive--; - return(RetCode); -} - - -#ifndef SFX_MODULE -long File::Copy(File &Dest,Int64 Length) -{ - Array Buffer(0x10000); - long CopySize=0; - bool CopyAll=(Length==INT64ERR); - - while (CopyAll || Length>0) - { - Wait(); - int SizeToRead=(!CopyAll && Length=NM || *s==0) - IgnoreAscii=true; - if (Wide && (PosW>=NM || PathW[PosW]==0) || !Wide && IgnoreAscii) - break; - if (Wide && PathW[PosW]==CPATHDIVIDER || !Wide && *s==CPATHDIVIDER) - { - wchar *DirPtrW=NULL,DirNameW[NM]; - if (Wide) - { - strncpyw(DirNameW,PathW,PosW); - DirNameW[PosW]=0; - DirPtrW=DirNameW; - } - char DirName[NM]; - if (IgnoreAscii) - WideToChar(DirPtrW,DirName); - else - { -#ifndef DBCS_SUPPORTED - if (*s!=CPATHDIVIDER) - for (const char *n=s;*n!=0 && n-PathIsSet(); - bool sc=ftc!=NULL && ftc->IsSet(); - bool sa=fta!=NULL && fta->IsSet(); - - unsigned int DirAttr=GetFileAttr(Name); - bool ResetAttr=(DirAttr!=0xffffffff && (DirAttr & FA_RDONLY)!=0); - if (ResetAttr) - SetFileAttr(Name,NULL,0); - HANDLE hFile=CreateFile(Name,GENERIC_WRITE,FILE_SHARE_READ|FILE_SHARE_WRITE, - NULL,OPEN_EXISTING,FILE_FLAG_BACKUP_SEMANTICS,NULL); - if (hFile==INVALID_HANDLE_VALUE) - return; - FILETIME fm,fc,fa; - if (sm) - ftm->GetWin32(&fm); - if (sc) - ftc->GetWin32(&fc); - if (sa) - fta->GetWin32(&fa); - SetFileTime(hFile,sc ? &fc:NULL,sa ? &fa:NULL,sm ? &fm:NULL); - CloseHandle(hFile); - if (ResetAttr) - SetFileAttr(Name,NULL,DirAttr); -#endif -#if defined(_UNIX) || defined(_EMX) - File::SetCloseFileTimeByName(Name,ftm,fta); -#endif -} - - -bool IsRemovable(const char *Name) -{ -#ifdef _WIN_32 - char Root[NM]; - GetPathRoot(Name,Root); - int Type=GetDriveType(*Root ? Root:NULL); - return(Type==DRIVE_REMOVABLE || Type==DRIVE_CDROM); -#elif defined(_EMX) - char Drive=etoupper(Name[0]); - return((Drive=='A' || Drive=='B') && Name[1]==':'); -#else - return(false); -#endif -} - - -#ifndef SFX_MODULE -Int64 GetFreeDisk(const char *Name) -{ -#ifdef _WIN_32 - char Root[NM]; - GetPathRoot(Name,Root); - - typedef BOOL (WINAPI *GETDISKFREESPACEEX)( - LPCTSTR,PULARGE_INTEGER,PULARGE_INTEGER,PULARGE_INTEGER - ); - static GETDISKFREESPACEEX pGetDiskFreeSpaceEx=NULL; - - if (pGetDiskFreeSpaceEx==NULL) - { - HMODULE hKernel=GetModuleHandle("kernel32.dll"); - if (hKernel!=NULL) - pGetDiskFreeSpaceEx=(GETDISKFREESPACEEX)GetProcAddress(hKernel,"GetDiskFreeSpaceExA"); - } - if (pGetDiskFreeSpaceEx!=NULL) - { - GetFilePath(Name,Root,ASIZE(Root)); - ULARGE_INTEGER uiTotalSize,uiTotalFree,uiUserFree; - uiUserFree.u.LowPart=uiUserFree.u.HighPart=0; - if (pGetDiskFreeSpaceEx(*Root ? Root:NULL,&uiUserFree,&uiTotalSize,&uiTotalFree) && - uiUserFree.u.HighPart<=uiTotalFree.u.HighPart) - return(int32to64(uiUserFree.u.HighPart,uiUserFree.u.LowPart)); - } - - DWORD SectorsPerCluster,BytesPerSector,FreeClusters,TotalClusters; - if (!GetDiskFreeSpace(*Root ? Root:NULL,&SectorsPerCluster,&BytesPerSector,&FreeClusters,&TotalClusters)) - return(1457664); - Int64 FreeSize=SectorsPerCluster*BytesPerSector; - FreeSize=FreeSize*FreeClusters; - return(FreeSize); -#elif defined(_BEOS) - char Root[NM]; - GetFilePath(Name,Root,ASIZE(Root)); - dev_t Dev=dev_for_path(*Root ? Root:"."); - if (Dev<0) - return(1457664); - fs_info Info; - if (fs_stat_dev(Dev,&Info)!=0) - return(1457664); - Int64 FreeSize=Info.block_size; - FreeSize=FreeSize*Info.free_blocks; - return(FreeSize); -#elif defined(_UNIX) - return(1457664); -#elif defined(_EMX) - int Drive=(!isalpha(Name[0]) || Name[1]!=':') ? 0:etoupper(Name[0])-'A'+1; -#ifndef _DJGPP - if (_osmode == OS2_MODE) - { - FSALLOCATE fsa; - if (DosQueryFSInfo(Drive,1,&fsa,sizeof(fsa))!=0) - return(1457664); - Int64 FreeSize=fsa.cSectorUnit*fsa.cbSector; - FreeSize=FreeSize*fsa.cUnitAvail; - return(FreeSize); - } - else -#endif - { - union REGS regs,outregs; - memset(®s,0,sizeof(regs)); - regs.h.ah=0x36; - regs.h.dl=Drive; -#ifdef _DJGPP - int86 (0x21,®s,&outregs); -#else - _int86 (0x21,®s,&outregs); -#endif - if (outregs.x.ax==0xffff) - return(1457664); - Int64 FreeSize=outregs.x.ax*outregs.x.cx; - FreeSize=FreeSize*outregs.x.bx; - return(FreeSize); - } -#else - #define DISABLEAUTODETECT - return(1457664); -#endif -} -#endif - - -bool FileExist(const char *Name,const wchar *NameW) -{ -#ifdef _WIN_32 - if (WinNT() && NameW!=NULL && *NameW!=0) - return(GetFileAttributesW(NameW)!=0xffffffff); - else - return(GetFileAttributes(Name)!=0xffffffff); -#elif defined(ENABLE_ACCESS) - return(access(Name,0)==0); -#else - struct FindData FD; - return(FindFile::FastFind(Name,NameW,&FD)); -#endif -} - - -bool WildFileExist(const char *Name,const wchar *NameW) -{ - if (IsWildcard(Name,NameW)) - { - FindFile Find; - Find.SetMask(Name); - Find.SetMaskW(NameW); - struct FindData fd; - return(Find.Next(&fd)); - } - return(FileExist(Name,NameW)); -} - - -bool IsDir(uint Attr) -{ -#if defined (_WIN_32) || defined(_EMX) - return(Attr!=0xffffffff && (Attr & 0x10)!=0); -#endif -#if defined(_UNIX) - return((Attr & 0xF000)==0x4000); -#endif -} - - -bool IsUnreadable(uint Attr) -{ -#if defined(_UNIX) && defined(S_ISFIFO) && defined(S_ISSOCK) && defined(S_ISCHR) - return(S_ISFIFO(Attr) || S_ISSOCK(Attr) || S_ISCHR(Attr)); -#endif - return(false); -} - - -bool IsLabel(uint Attr) -{ -#if defined (_WIN_32) || defined(_EMX) - return((Attr & 8)!=0); -#else - return(false); -#endif -} - - -bool IsLink(uint Attr) -{ -#ifdef _UNIX - return((Attr & 0xF000)==0xA000); -#else - return(false); -#endif -} - - - - - - -bool IsDeleteAllowed(uint FileAttr) -{ -#if defined(_WIN_32) || defined(_EMX) - return((FileAttr & (FA_RDONLY|FA_SYSTEM|FA_HIDDEN))==0); -#else - return((FileAttr & (S_IRUSR|S_IWUSR))==(S_IRUSR|S_IWUSR)); -#endif -} - - -void PrepareToDelete(const char *Name,const wchar *NameW) -{ -#if defined(_WIN_32) || defined(_EMX) - SetFileAttr(Name,NameW,0); -#endif -#ifdef _UNIX - chmod(Name,S_IRUSR|S_IWUSR|S_IXUSR); -#endif -} - - -uint GetFileAttr(const char *Name,const wchar *NameW) -{ -#ifdef _WIN_32 - if (WinNT() && NameW!=NULL && *NameW!=0) - return(GetFileAttributesW(NameW)); - else - return(GetFileAttributes(Name)); -#elif defined(_DJGPP) - return(_chmod(Name,0)); -#else - struct stat st; - if (stat(Name,&st)!=0) - return(0); -#ifdef _EMX - return(st.st_attr); -#else - return(st.st_mode); -#endif -#endif -} - - -bool SetFileAttr(const char *Name,const wchar *NameW,uint Attr) -{ - bool Success; -#ifdef _WIN_32 - if (WinNT() && NameW!=NULL && *NameW!=0) - Success=SetFileAttributesW(NameW,Attr)!=0; - else - Success=SetFileAttributes(Name,Attr)!=0; -#elif defined(_DJGPP) - Success=_chmod(Name,1,Attr)!=-1; -#elif defined(_EMX) - Success=__chmod(Name,1,Attr)!=-1; -#elif defined(_UNIX) - Success=chmod(Name,(mode_t)Attr)==0; -#else - Success=false; -#endif - return(Success); -} - - -void ConvertNameToFull(const char *Src,char *Dest) -{ -#ifdef _WIN_32 -#ifndef _WIN_CE - char FullName[NM],*NamePtr; - if (GetFullPathName(Src,sizeof(FullName),FullName,&NamePtr)) - strcpy(Dest,FullName); - else -#endif - if (Src!=Dest) - strcpy(Dest,Src); -#else - char FullName[NM]; - if (IsPathDiv(*Src) || IsDiskLetter(Src)) - strcpy(FullName,Src); - else - { - getcwd(FullName,sizeof(FullName)); - AddEndSlash(FullName); - strcat(FullName,Src); - } - strcpy(Dest,FullName); -#endif -} - - -#ifndef SFX_MODULE -void ConvertNameToFull(const wchar *Src,wchar *Dest) -{ - if (Src==NULL || *Src==0) - { - *Dest=0; - return; - } -#ifdef _WIN_32 -#ifndef _WIN_CE - if (WinNT()) -#endif - { -#ifndef _WIN_CE - wchar FullName[NM],*NamePtr; - if (GetFullPathNameW(Src,sizeof(FullName)/sizeof(FullName[0]),FullName,&NamePtr)) - strcpyw(Dest,FullName); - else -#endif - if (Src!=Dest) - strcpyw(Dest,Src); - } -#ifndef _WIN_CE - else - { - char AnsiName[NM]; - WideToChar(Src,AnsiName); - ConvertNameToFull(AnsiName,AnsiName); - CharToWide(AnsiName,Dest); - } -#endif -#else - char AnsiName[NM]; - WideToChar(Src,AnsiName); - ConvertNameToFull(AnsiName,AnsiName); - CharToWide(AnsiName,Dest); -#endif -} -#endif - - -#ifndef SFX_MODULE -char *MkTemp(char *Name) -{ - int Length=strlen(Name); - if (Length<=6) - return(NULL); - int Random=clock(); - for (int Attempt=0;;Attempt++) - { - sprintf(Name+Length-6,"%06u",Random+Attempt); - Name[Length-4]='.'; - if (!FileExist(Name)) - break; - if (Attempt==1000) - return(NULL); - } - return(Name); -} -#endif - - - - -#ifndef SFX_MODULE -uint CalcFileCRC(File *SrcFile,Int64 Size,CALCCRC_SHOWMODE ShowMode) -{ - SaveFilePos SavePos(*SrcFile); - const int BufSize=0x10000; - Array Data(BufSize); - Int64 BlockCount=0; - uint DataCRC=0xffffffff; - int ReadSize; - -#if !defined(SILENT) && !defined(_WIN_CE) - Int64 FileLength=SrcFile->FileLength(); - if (ShowMode!=CALCCRC_SHOWNONE) - { - mprintf(St(MCalcCRC)); - mprintf(" "); - } - -#endif - - SrcFile->Seek(0,SEEK_SET); - while ((ReadSize=SrcFile->Read(&Data[0],int64to32(Size==INT64ERR ? Int64(BufSize):Min(Int64(BufSize),Size))))!=0) - { - ++BlockCount; - if ((BlockCount & 15)==0) - { -#if !defined(SILENT) && !defined(_WIN_CE) - if (ShowMode==CALCCRC_SHOWALL) - mprintf("\b\b\b\b%3d%%",ToPercent(BlockCount*Int64(BufSize),FileLength)); -#endif - Wait(); - } - DataCRC=CRC(DataCRC,&Data[0],ReadSize); - if (Size!=INT64ERR) - Size-=ReadSize; - } -#if !defined(SILENT) && !defined(_WIN_CE) - if (ShowMode==CALCCRC_SHOWALL) - mprintf("\b\b\b\b "); -#endif - return(DataCRC^0xffffffff); -} -#endif - - -bool RenameFile(const char *SrcName,const wchar *SrcNameW,const char *DestName,const wchar *DestNameW) -{ - return(rename(SrcName,DestName)==0); -} - - -bool DelFile(const char *Name) -{ - return(DelFile(Name,NULL)); -} - - -bool DelFile(const char *Name,const wchar *NameW) -{ - return(remove(Name)==0); -} - - -bool DelDir(const char *Name) -{ - return(DelDir(Name,NULL)); -} - - -bool DelDir(const char *Name,const wchar *NameW) -{ - return(rmdir(Name)==0); -} - - -#if defined(_WIN_32) && !defined(_WIN_CE) -bool SetFileCompression(char *Name,wchar *NameW,bool State) -{ - wchar FileNameW[NM]; - GetWideName(Name,NameW,FileNameW); - HANDLE hFile=CreateFileW(FileNameW,FILE_READ_DATA|FILE_WRITE_DATA, - FILE_SHARE_READ|FILE_SHARE_WRITE,NULL,OPEN_EXISTING, - FILE_FLAG_BACKUP_SEMANTICS|FILE_FLAG_SEQUENTIAL_SCAN,NULL); - if (hFile==INVALID_HANDLE_VALUE) - return(false); - SHORT NewState=State ? COMPRESSION_FORMAT_DEFAULT:COMPRESSION_FORMAT_NONE; - DWORD Result; - int RetCode=DeviceIoControl(hFile,FSCTL_SET_COMPRESSION,&NewState, - sizeof(NewState),NULL,0,&Result,NULL); - CloseHandle(hFile); - return(RetCode!=0); -} -#endif diff --git a/src/bin/unrar/filefn.hpp b/src/bin/unrar/filefn.hpp deleted file mode 100644 index ec6cba528a..0000000000 --- a/src/bin/unrar/filefn.hpp +++ /dev/null @@ -1,41 +0,0 @@ -#ifndef _RAR_FILEFN_ -#define _RAR_FILEFN_ - -enum MKDIR_CODE {MKDIR_SUCCESS,MKDIR_ERROR,MKDIR_BADPATH}; - -MKDIR_CODE MakeDir(const char *Name,const wchar *NameW,uint Attr); -bool CreatePath(const char *Path,const wchar *PathW,bool SkipLastName); -void SetDirTime(const char *Name,RarTime *ftm,RarTime *ftc,RarTime *fta); -bool IsRemovable(const char *Name); -Int64 GetFreeDisk(const char *Name); -bool FileExist(const char *Name,const wchar *NameW=NULL); -bool WildFileExist(const char *Name,const wchar *NameW=NULL); -bool IsDir(uint Attr); -bool IsUnreadable(uint Attr); -bool IsLabel(uint Attr); -bool IsLink(uint Attr); -void SetSFXMode(const char *FileName); -void EraseDiskContents(const char *FileName); -bool IsDeleteAllowed(uint FileAttr); -void PrepareToDelete(const char *Name,const wchar *NameW=NULL); -uint GetFileAttr(const char *Name,const wchar *NameW=NULL); -bool SetFileAttr(const char *Name,const wchar *NameW,uint Attr); -void ConvertNameToFull(const char *Src,char *Dest); -void ConvertNameToFull(const wchar *Src,wchar *Dest); -char* MkTemp(char *Name); - - -enum CALCCRC_SHOWMODE {CALCCRC_SHOWNONE,CALCCRC_SHOWTEXT,CALCCRC_SHOWALL}; -uint CalcFileCRC(File *SrcFile,Int64 Size=INT64ERR,CALCCRC_SHOWMODE ShowMode=CALCCRC_SHOWNONE); - -bool RenameFile(const char *SrcName,const wchar *SrcNameW,const char *DestName,const wchar *DestNameW); -bool DelFile(const char *Name); -bool DelFile(const char *Name,const wchar *NameW); -bool DelDir(const char *Name); -bool DelDir(const char *Name,const wchar *NameW); - -#if defined(_WIN_32) && !defined(_WIN_CE) -bool SetFileCompression(char *Name,wchar *NameW,bool State); -#endif - -#endif diff --git a/src/bin/unrar/filestr.cpp b/src/bin/unrar/filestr.cpp deleted file mode 100644 index 55e79a1fd7..0000000000 --- a/src/bin/unrar/filestr.cpp +++ /dev/null @@ -1,145 +0,0 @@ -#include "rar.hpp" - -static bool IsUnicode(byte *Data,int Size); - -bool ReadTextFile(char *Name,StringList *List,bool Config,bool AbortOnError, - RAR_CHARSET SrcCharset,bool Unquote,bool SkipComments) -{ - char FileName[NM]; - if (Config) - GetConfigName(Name,FileName,true); - else - strcpy(FileName,Name); - - File SrcFile; - if (*FileName) - { - bool OpenCode=AbortOnError ? SrcFile.WOpen(FileName):SrcFile.Open(FileName); - - if (!OpenCode) - { - if (AbortOnError) - ErrHandler.Exit(OPEN_ERROR); - return(false); - } - } - else - SrcFile.SetHandleType(FILE_HANDLESTD); - - unsigned int DataSize=0,ReadSize; - const int ReadBlock=1024; - Array Data(ReadBlock+5); - while ((ReadSize=SrcFile.Read(&Data[DataSize],ReadBlock))!=0) - { - DataSize+=ReadSize; - Data.Add(ReadSize); - } - - memset(&Data[DataSize],0,5); - - if (SrcCharset==RCH_UNICODE || - SrcCharset==RCH_DEFAULT && IsUnicode((byte *)&Data[0],DataSize)) - { - // Unicode in native system format, can be more than 2 bytes per character - Array DataW(Data.Size()/2+1); - for (int I=2;I AnsiName; - - while (*CurStr!=0) - { - wchar *NextStr=CurStr,*CmtPtr=NULL; - while (*NextStr!='\r' && *NextStr!='\n' && *NextStr!=0) - { - if (SkipComments && NextStr[0]=='/' && NextStr[1]=='/') - { - *NextStr=0; - CmtPtr=NextStr; - } - NextStr++; - } - *NextStr=0; - for (wchar *SpacePtr=(CmtPtr ? CmtPtr:NextStr)-1;SpacePtr>=CurStr;SpacePtr--) - { - if (*SpacePtr!=' ' && *SpacePtr!='\t') - break; - *SpacePtr=0; - } - if (*CurStr) - { - int Length=strlenw(CurStr); - int AddSize=4*(Length-AnsiName.Size()+1); - if (AddSize>0) - AnsiName.Add(AddSize); - if (Unquote && *CurStr=='\"' && CurStr[Length-1]=='\"') - { - CurStr[Length-1]=0; - CurStr++; - } - WideToChar(CurStr,&AnsiName[0],AnsiName.Size()); - List->AddString(&AnsiName[0],CurStr); - } - CurStr=NextStr+1; - while (*CurStr=='\r' || *CurStr=='\n') - CurStr++; - } - } - else - { - char *CurStr=&Data[0]; - while (*CurStr!=0) - { - char *NextStr=CurStr,*CmtPtr=NULL; - while (*NextStr!='\r' && *NextStr!='\n' && *NextStr!=0) - { - if (SkipComments && NextStr[0]=='/' && NextStr[1]=='/') - { - *NextStr=0; - CmtPtr=NextStr; - } - NextStr++; - } - *NextStr=0; - for (char *SpacePtr=(CmtPtr ? CmtPtr:NextStr)-1;SpacePtr>=CurStr;SpacePtr--) - { - if (*SpacePtr!=' ' && *SpacePtr!='\t') - break; - *SpacePtr=0; - } - if (*CurStr) - { - if (Unquote && *CurStr=='\"') - { - int Length=strlen(CurStr); - if (CurStr[Length-1]=='\"') - { - CurStr[Length-1]=0; - CurStr++; - } - } -#if defined(_WIN_32) - if (SrcCharset==RCH_OEM) - OemToChar(CurStr,CurStr); -#endif - List->AddString(CurStr); - } - CurStr=NextStr+1; - while (*CurStr=='\r' || *CurStr=='\n') - CurStr++; - } - } - return(true); -} - - -bool IsUnicode(byte *Data,int Size) -{ - if (Size<4 || Data[0]!=0xff || Data[1]!=0xfe) - return(false); - for (int I=2;IError=false; - if (*FindMask==0) - return(false); -#ifdef _WIN_32 - if (FirstCall) - { - if ((hFind=Win32Find(INVALID_HANDLE_VALUE,FindMask,FindMaskW,fd))==INVALID_HANDLE_VALUE) - return(false); - } - else - if (Win32Find(hFind,FindMask,FindMaskW,fd)==INVALID_HANDLE_VALUE) - return(false); -#else - if (FirstCall) - { - char DirName[NM]; - strcpy(DirName,FindMask); - RemoveNameFromPath(DirName); - if (*DirName==0) - strcpy(DirName,"."); -/* - else - { - int Length=strlen(DirName); - if (Length>1 && DirName[Length-1]==CPATHDIVIDER && (Length!=3 || !IsDriveDiv(DirName[1]))) - DirName[Length-1]=0; - } -*/ - if ((dirp=opendir(DirName))==NULL) - { - fd->Error=(errno!=ENOENT); - return(false); - } - } - while (1) - { - struct dirent *ent=readdir(dirp); - if (ent==NULL) - return(false); - if (strcmp(ent->d_name,".")==0 || strcmp(ent->d_name,"..")==0) - continue; - if (CmpName(FindMask,ent->d_name,MATCH_NAMES)) - { - char FullName[NM]; - strcpy(FullName,FindMask); - *PointToName(FullName)=0; - if (strlen(FullName)+strlen(ent->d_name)>=ASIZE(FullName)-1) - { -#ifndef SILENT - Log(NULL,"\n%s%s",FullName,ent->d_name); - Log(NULL,St(MPathTooLong)); -#endif - return(false); - } - strcat(FullName,ent->d_name); - if (!FastFind(FullName,NULL,fd,GetSymLink)) - { - ErrHandler.OpenErrorMsg(FullName); - continue; - } - strcpy(fd->Name,FullName); - break; - } - } - *fd->NameW=0; -#ifdef _APPLE - if (!LowAscii(fd->Name)) - UtfToWide(fd->Name,fd->NameW,sizeof(fd->NameW)); -#elif defined(UNICODE_SUPPORTED) - if (!LowAscii(fd->Name) && UnicodeEnabled()) - CharToWide(fd->Name,fd->NameW); -#endif -#endif - fd->IsDir=IsDir(fd->FileAttr); - FirstCall=FALSE; - char *Name=PointToName(fd->Name); - if (strcmp(Name,".")==0 || strcmp(Name,"..")==0) - return(Next(fd)); - return(true); -} - - -bool FindFile::FastFind(const char *FindMask,const wchar *FindMaskW,struct FindData *fd,bool GetSymLink) -{ - fd->Error=false; -#ifndef _UNIX - if (IsWildcard(FindMask,FindMaskW)) - return(false); -#endif -#ifdef _WIN_32 - HANDLE hFind=Win32Find(INVALID_HANDLE_VALUE,FindMask,FindMaskW,fd); - if (hFind==INVALID_HANDLE_VALUE) - return(false); - FindClose(hFind); -#else - struct stat st; - if (GetSymLink) - { -#ifdef SAVE_LINKS - if (lstat(FindMask,&st)!=0) -#else - if (stat(FindMask,&st)!=0) -#endif - { - fd->Error=(errno!=ENOENT); - return(false); - } - } - else - if (stat(FindMask,&st)!=0) - { - fd->Error=(errno!=ENOENT); - return(false); - } -#ifdef _DJGPP - fd->FileAttr=_chmod(FindMask,0); -#elif defined(_EMX) - fd->FileAttr=st.st_attr; -#else - fd->FileAttr=st.st_mode; -#endif - fd->IsDir=IsDir(st.st_mode); - fd->Size=st.st_size; - fd->mtime=st.st_mtime; - fd->atime=st.st_atime; - fd->ctime=st.st_ctime; - fd->FileTime=fd->mtime.GetDos(); - strcpy(fd->Name,FindMask); - - *fd->NameW=0; -#ifdef _APPLE - if (!LowAscii(fd->Name)) - UtfToWide(fd->Name,fd->NameW,sizeof(fd->NameW)); -#elif defined(UNICODE_SUPPORTED) - if (!LowAscii(fd->Name) && UnicodeEnabled()) - CharToWide(fd->Name,fd->NameW); -#endif -#endif - fd->IsDir=IsDir(fd->FileAttr); - return(true); -} - - -#ifdef _WIN_32 -HANDLE FindFile::Win32Find(HANDLE hFind,const char *Mask,const wchar *MaskW,struct FindData *fd) -{ -#ifndef _WIN_CE - if (WinNT()) -#endif - { - wchar WideMask[NM]; - if (MaskW!=NULL && *MaskW!=0) - strcpyw(WideMask,MaskW); - else - CharToWide(Mask,WideMask); - - WIN32_FIND_DATAW FindData; - if (hFind==INVALID_HANDLE_VALUE) - { - hFind=FindFirstFileW(WideMask,&FindData); - if (hFind==INVALID_HANDLE_VALUE) - { - int SysErr=GetLastError(); - fd->Error=(SysErr!=ERROR_FILE_NOT_FOUND && - SysErr!=ERROR_PATH_NOT_FOUND && - SysErr!=ERROR_NO_MORE_FILES); - } - } - else - if (!FindNextFileW(hFind,&FindData)) - { - hFind=INVALID_HANDLE_VALUE; - fd->Error=GetLastError()!=ERROR_NO_MORE_FILES; - } - - if (hFind!=INVALID_HANDLE_VALUE) - { - strcpyw(fd->NameW,WideMask); - strcpyw(PointToName(fd->NameW),FindData.cFileName); - WideToChar(fd->NameW,fd->Name); - fd->Size=int32to64(FindData.nFileSizeHigh,FindData.nFileSizeLow); - fd->FileAttr=FindData.dwFileAttributes; - WideToChar(FindData.cAlternateFileName,fd->ShortName); - fd->ftCreationTime=FindData.ftCreationTime; - fd->ftLastAccessTime=FindData.ftLastAccessTime; - fd->ftLastWriteTime=FindData.ftLastWriteTime; - fd->mtime=FindData.ftLastWriteTime; - fd->ctime=FindData.ftCreationTime; - fd->atime=FindData.ftLastAccessTime; - fd->FileTime=fd->mtime.GetDos(); - -#ifndef _WIN_CE - if (LowAscii(fd->NameW)) - *fd->NameW=0; -#endif - } - } -#ifndef _WIN_CE - else - { - char CharMask[NM]; - if (Mask!=NULL && *Mask!=0) - strcpy(CharMask,Mask); - else - WideToChar(MaskW,CharMask); - - WIN32_FIND_DATA FindData; - if (hFind==INVALID_HANDLE_VALUE) - { - hFind=FindFirstFile(CharMask,&FindData); - if (hFind==INVALID_HANDLE_VALUE) - { - int SysErr=GetLastError(); - fd->Error=SysErr!=ERROR_FILE_NOT_FOUND && SysErr!=ERROR_PATH_NOT_FOUND; - } - } - else - if (!FindNextFile(hFind,&FindData)) - { - hFind=INVALID_HANDLE_VALUE; - fd->Error=GetLastError()!=ERROR_NO_MORE_FILES; - } - - if (hFind!=INVALID_HANDLE_VALUE) - { - strcpy(fd->Name,CharMask); - strcpy(PointToName(fd->Name),FindData.cFileName); - CharToWide(fd->Name,fd->NameW); - fd->Size=int32to64(FindData.nFileSizeHigh,FindData.nFileSizeLow); - fd->FileAttr=FindData.dwFileAttributes; - strcpy(fd->ShortName,FindData.cAlternateFileName); - fd->ftCreationTime=FindData.ftCreationTime; - fd->ftLastAccessTime=FindData.ftLastAccessTime; - fd->ftLastWriteTime=FindData.ftLastWriteTime; - fd->mtime=FindData.ftLastWriteTime; - fd->ctime=FindData.ftCreationTime; - fd->atime=FindData.ftLastAccessTime; - fd->FileTime=fd->mtime.GetDos(); - if (LowAscii(fd->Name)) - *fd->NameW=0; - } - } -#endif - return(hFind); -} -#endif - diff --git a/src/bin/unrar/find.hpp b/src/bin/unrar/find.hpp deleted file mode 100644 index 81548199c3..0000000000 --- a/src/bin/unrar/find.hpp +++ /dev/null @@ -1,48 +0,0 @@ -#ifndef _RAR_FINDDATA_ -#define _RAR_FINDDATA_ - -struct FindData -{ - char Name[NM]; - wchar NameW[NM]; - Int64 Size; - uint FileAttr; - uint FileTime; - bool IsDir; - RarTime mtime; - RarTime ctime; - RarTime atime; -#ifdef _WIN_32 - char ShortName[NM]; - FILETIME ftCreationTime; - FILETIME ftLastAccessTime; - FILETIME ftLastWriteTime; -#endif - bool Error; -}; - -class FindFile -{ - private: -#ifdef _WIN_32 - static HANDLE Win32Find(HANDLE hFind,const char *Mask,const wchar *MaskW,struct FindData *fd); -#endif - - char FindMask[NM]; - wchar FindMaskW[NM]; - int FirstCall; -#ifdef _WIN_32 - HANDLE hFind; -#else - DIR *dirp; -#endif - public: - FindFile(); - ~FindFile(); - void SetMask(const char *FindMask); - void SetMaskW(const wchar *FindMaskW); - bool Next(struct FindData *fd,bool GetSymLink=false); - static bool FastFind(const char *FindMask,const wchar *FindMaskW,struct FindData *fd,bool GetSymLink=false); -}; - -#endif diff --git a/src/bin/unrar/getbits.cpp b/src/bin/unrar/getbits.cpp deleted file mode 100644 index 71ecfc875c..0000000000 --- a/src/bin/unrar/getbits.cpp +++ /dev/null @@ -1,24 +0,0 @@ -#include "rar.hpp" - -BitInput::BitInput() -{ - InBuf=new byte[MAX_SIZE]; -} - - -BitInput::~BitInput() -{ - delete[] InBuf; -} - - -void BitInput::faddbits(int Bits) -{ - addbits(Bits); -} - - -unsigned int BitInput::fgetbits() -{ - return(getbits()); -} diff --git a/src/bin/unrar/getbits.hpp b/src/bin/unrar/getbits.hpp deleted file mode 100644 index eff4dafcbf..0000000000 --- a/src/bin/unrar/getbits.hpp +++ /dev/null @@ -1,38 +0,0 @@ -#ifndef _RAR_GETBITS_ -#define _RAR_GETBITS_ - -class BitInput -{ - public: - enum BufferSize {MAX_SIZE=0x8000}; - protected: - int InAddr,InBit; - public: - BitInput(); - ~BitInput(); - - byte *InBuf; - - void InitBitInput() - { - InAddr=InBit=0; - } - void addbits(int Bits) - { - Bits+=InBit; - InAddr+=Bits>>3; - InBit=Bits&7; - } - unsigned int getbits() - { - unsigned int BitField=(uint)InBuf[InAddr] << 16; - BitField|=(uint)InBuf[InAddr+1] << 8; - BitField|=(uint)InBuf[InAddr+2]; - BitField >>= (8-InBit); - return(BitField & 0xffff); - } - void faddbits(int Bits); - unsigned int fgetbits(); - bool Overflow(int IncPtr) {return(InAddr+IncPtr>=MAX_SIZE);} -}; -#endif diff --git a/src/bin/unrar/global.cpp b/src/bin/unrar/global.cpp deleted file mode 100644 index 593a057cbf..0000000000 --- a/src/bin/unrar/global.cpp +++ /dev/null @@ -1,4 +0,0 @@ -#define INCLUDEGLOBAL - - -#include "rar.hpp" diff --git a/src/bin/unrar/global.hpp b/src/bin/unrar/global.hpp deleted file mode 100644 index 35c6cf9130..0000000000 --- a/src/bin/unrar/global.hpp +++ /dev/null @@ -1,14 +0,0 @@ -#ifndef _RAR_GLOBAL_ -#define _RAR_GLOBAL_ - -#ifdef INCLUDEGLOBAL - #define EXTVAR -#else - #define EXTVAR extern -#endif - -EXTVAR ErrorHandler ErrHandler; - - - -#endif diff --git a/src/bin/unrar/headers.hpp b/src/bin/unrar/headers.hpp deleted file mode 100644 index acf597d758..0000000000 --- a/src/bin/unrar/headers.hpp +++ /dev/null @@ -1,306 +0,0 @@ -#ifndef _RAR_HEADERS_ -#define _RAR_HEADERS_ - -#define SIZEOF_MARKHEAD 7 -#define SIZEOF_OLDMHD 7 -#define SIZEOF_NEWMHD 13 -#define SIZEOF_OLDLHD 21 -#define SIZEOF_NEWLHD 32 -#define SIZEOF_SHORTBLOCKHEAD 7 -#define SIZEOF_LONGBLOCKHEAD 11 -#define SIZEOF_SUBBLOCKHEAD 14 -#define SIZEOF_COMMHEAD 13 -#define SIZEOF_PROTECTHEAD 26 -#define SIZEOF_AVHEAD 14 -#define SIZEOF_SIGNHEAD 15 -#define SIZEOF_UOHEAD 18 -#define SIZEOF_MACHEAD 22 -#define SIZEOF_EAHEAD 24 -#define SIZEOF_BEEAHEAD 24 -#define SIZEOF_STREAMHEAD 26 - -#define PACK_VER 29 -#define PACK_CRYPT_VER 29 -#define UNP_VER 36 -#define CRYPT_VER 29 -#define AV_VER 20 -#define PROTECT_VER 20 - -#define MHD_VOLUME 0x0001 -#define MHD_COMMENT 0x0002 -#define MHD_LOCK 0x0004 -#define MHD_SOLID 0x0008 -#define MHD_PACK_COMMENT 0x0010 -#define MHD_NEWNUMBERING 0x0010 -#define MHD_AV 0x0020 -#define MHD_PROTECT 0x0040 -#define MHD_PASSWORD 0x0080 -#define MHD_FIRSTVOLUME 0x0100 -#define MHD_ENCRYPTVER 0x0200 - -#define LHD_SPLIT_BEFORE 0x0001 -#define LHD_SPLIT_AFTER 0x0002 -#define LHD_PASSWORD 0x0004 -#define LHD_COMMENT 0x0008 -#define LHD_SOLID 0x0010 - -#define LHD_WINDOWMASK 0x00e0 -#define LHD_WINDOW64 0x0000 -#define LHD_WINDOW128 0x0020 -#define LHD_WINDOW256 0x0040 -#define LHD_WINDOW512 0x0060 -#define LHD_WINDOW1024 0x0080 -#define LHD_WINDOW2048 0x00a0 -#define LHD_WINDOW4096 0x00c0 -#define LHD_DIRECTORY 0x00e0 - -#define LHD_LARGE 0x0100 -#define LHD_UNICODE 0x0200 -#define LHD_SALT 0x0400 -#define LHD_VERSION 0x0800 -#define LHD_EXTTIME 0x1000 -#define LHD_EXTFLAGS 0x2000 - -#define SKIP_IF_UNKNOWN 0x4000 -#define LONG_BLOCK 0x8000 - -#define EARC_NEXT_VOLUME 0x0001 // not last volume -#define EARC_DATACRC 0x0002 -#define EARC_REVSPACE 0x0004 -#define EARC_VOLNUMBER 0x0008 - -enum HEADER_TYPE { - MARK_HEAD=0x72,MAIN_HEAD=0x73,FILE_HEAD=0x74,COMM_HEAD=0x75,AV_HEAD=0x76, - SUB_HEAD=0x77,PROTECT_HEAD=0x78,SIGN_HEAD=0x79,NEWSUB_HEAD=0x7a, - ENDARC_HEAD=0x7b -}; - -enum { EA_HEAD=0x100,UO_HEAD=0x101,MAC_HEAD=0x102,BEEA_HEAD=0x103, - NTACL_HEAD=0x104,STREAM_HEAD=0x105 }; - -enum HOST_SYSTEM { - HOST_MSDOS=0,HOST_OS2=1,HOST_WIN32=2,HOST_UNIX=3,HOST_MACOS=4, - HOST_BEOS=5,HOST_MAX -}; - -#define SUBHEAD_TYPE_CMT "CMT" -#define SUBHEAD_TYPE_ACL "ACL" -#define SUBHEAD_TYPE_STREAM "STM" -#define SUBHEAD_TYPE_UOWNER "UOW" -#define SUBHEAD_TYPE_AV "AV" -#define SUBHEAD_TYPE_RR "RR" -#define SUBHEAD_TYPE_OS2EA "EA2" -#define SUBHEAD_TYPE_BEOSEA "EABE" - -/* new file inherits a subblock when updating a host file */ -#define SUBHEAD_FLAGS_INHERITED 0x80000000 - -#define SUBHEAD_FLAGS_CMT_UNICODE 0x00000001 - -struct OldMainHeader -{ - byte Mark[4]; - ushort HeadSize; - byte Flags; -}; - - -struct OldFileHeader -{ - uint PackSize; - uint UnpSize; - ushort FileCRC; - ushort HeadSize; - uint FileTime; - byte FileAttr; - byte Flags; - byte UnpVer; - byte NameSize; - byte Method; -}; - - -struct MarkHeader -{ - byte Mark[7]; -}; - - -struct BaseBlock -{ - ushort HeadCRC; - HEADER_TYPE HeadType;//byte - ushort Flags; - ushort HeadSize; - - bool IsSubBlock() - { - if (HeadType==SUB_HEAD) - return(true); - if (HeadType==NEWSUB_HEAD && (Flags & LHD_SOLID)!=0) - return(true); - return(false); - } -}; - -struct BlockHeader:BaseBlock -{ - union { - uint DataSize; - uint PackSize; - }; -}; - - -struct MainHeader:BaseBlock -{ - ushort HighPosAV; - uint PosAV; - byte EncryptVer; -}; - - -#define SALT_SIZE 8 - -struct FileHeader:BlockHeader -{ - uint UnpSize; - byte HostOS; - uint FileCRC; - uint FileTime; - byte UnpVer; - byte Method; - ushort NameSize; - union { - uint FileAttr; - uint SubFlags; - }; -/* optional */ - uint HighPackSize; - uint HighUnpSize; -/* names */ - char FileName[NM]; - wchar FileNameW[NM]; -/* optional */ - Array SubData; - byte Salt[SALT_SIZE]; - - RarTime mtime; - RarTime ctime; - RarTime atime; - RarTime arctime; -/* dummy */ - Int64 FullPackSize; - Int64 FullUnpSize; - - void Clear(int SubDataSize) - { - SubData.Alloc(SubDataSize); - Flags=LONG_BLOCK; - SubFlags=0; - } - - bool CmpName(const char *Name) - { - return(strcmp(FileName,Name)==0); - } - - FileHeader& operator = (FileHeader &hd) - { - SubData.Reset(); - memcpy(this,&hd,sizeof(*this)); - SubData.CleanData(); - SubData=hd.SubData; - return(*this); - } -}; - - -struct EndArcHeader:BaseBlock -{ - uint ArcDataCRC; - ushort VolNumber; -}; - - -struct SubBlockHeader:BlockHeader -{ - ushort SubType; - byte Level; -}; - - -struct CommentHeader:BaseBlock -{ - ushort UnpSize; - byte UnpVer; - byte Method; - ushort CommCRC; -}; - - -struct ProtectHeader:BlockHeader -{ - byte Version; - ushort RecSectors; - uint TotalBlocks; - byte Mark[8]; -}; - - -struct AVHeader:BaseBlock -{ - byte UnpVer; - byte Method; - byte AVVer; - uint AVInfoCRC; -}; - - -struct SignHeader:BaseBlock -{ - uint CreationTime; - ushort ArcNameSize; - ushort UserNameSize; -}; - - -struct UnixOwnersHeader:SubBlockHeader -{ - ushort OwnerNameSize; - ushort GroupNameSize; -/* dummy */ - char OwnerName[NM]; - char GroupName[NM]; -}; - - -struct EAHeader:SubBlockHeader -{ - uint UnpSize; - byte UnpVer; - byte Method; - uint EACRC; -}; - - -struct StreamHeader:SubBlockHeader -{ - uint UnpSize; - byte UnpVer; - byte Method; - uint StreamCRC; - ushort StreamNameSize; -/* dummy */ - byte StreamName[NM]; -}; - - -struct MacFInfoHeader:SubBlockHeader -{ - uint fileType; - uint fileCreator; -}; - - -#endif diff --git a/src/bin/unrar/int64.cpp b/src/bin/unrar/int64.cpp deleted file mode 100644 index 996d0ea62d..0000000000 --- a/src/bin/unrar/int64.cpp +++ /dev/null @@ -1,274 +0,0 @@ -#include "rar.hpp" - -#ifndef NATIVE_INT64 - -Int64::Int64() -{ -} - - -Int64::Int64(uint n) -{ - HighPart=0; - LowPart=n; -} - - -Int64::Int64(uint HighPart,uint LowPart) -{ - Int64::HighPart=HighPart; - Int64::LowPart=LowPart; -} - - -/* -Int64 Int64::operator = (Int64 n) -{ - HighPart=n.HighPart; - LowPart=n.LowPart; - return(*this); -} -*/ - - -Int64 Int64::operator << (int n) -{ - Int64 res=*this; - while (n--) - { - res.HighPart<<=1; - if (res.LowPart & 0x80000000) - res.HighPart|=1; - res.LowPart<<=1; - } - return(res); -} - - -Int64 Int64::operator >> (int n) -{ - Int64 res=*this; - while (n--) - { - res.LowPart>>=1; - if (res.HighPart & 1) - res.LowPart|=0x80000000; - res.HighPart>>=1; - } - return(res); -} - - -Int64 operator / (Int64 n1,Int64 n2) -{ - if (n1.HighPart==0 && n2.HighPart==0) - return(Int64(0,n1.LowPart/n2.LowPart)); - int ShiftCount=0; - while (n1>n2) - { - n2=n2<<1; - if (++ShiftCount>64) - return(0); - } - Int64 res=0; - while (ShiftCount-- >= 0) - { - res=res<<1; - if (n1>=n2) - { - n1-=n2; - ++res; - } - n2=n2>>1; - } - return(res); -} - - -Int64 operator * (Int64 n1,Int64 n2) -{ - if (n1<0x10000 && n2<0x10000) - return(Int64(0,n1.LowPart*n2.LowPart)); - Int64 res=0; - for (int I=0;I<64;I++) - { - if (n2.LowPart & 1) - res+=n1; - n1=n1<<1; - n2=n2>>1; - } - return(res); -} - - -Int64 operator % (Int64 n1,Int64 n2) -{ - if (n1.HighPart==0 && n2.HighPart==0) - return(Int64(0,n1.LowPart%n2.LowPart)); - return(n1-n1/n2*n2); -} - - -Int64 operator + (Int64 n1,Int64 n2) -{ - n1.LowPart+=n2.LowPart; - if (n1.LowPart (Int64 n1,Int64 n2) -{ - return((int)n1.HighPart>(int)n2.HighPart || n1.HighPart==n2.HighPart && n1.LowPart>n2.LowPart); -} - - -bool operator < (Int64 n1,Int64 n2) -{ - return((int)n1.HighPart<(int)n2.HighPart || n1.HighPart==n2.HighPart && n1.LowPart= (Int64 n1,Int64 n2) -{ - return(n1>n2 || n1==n2); -} - - -bool operator <= (Int64 n1,Int64 n2) -{ - return(n1='0' && *Str<='9') - { - n=n*10+*Str-'0'; - Str++; - } - return(n); -} diff --git a/src/bin/unrar/int64.hpp b/src/bin/unrar/int64.hpp deleted file mode 100644 index d2f34bb156..0000000000 --- a/src/bin/unrar/int64.hpp +++ /dev/null @@ -1,86 +0,0 @@ -#ifndef _RAR_INT64_ -#define _RAR_INT64_ - -#if defined(__BORLANDC__) || defined(_MSC_VER) -#define NATIVE_INT64 -typedef __int64 Int64; -#endif - -#if defined(__GNUC__) || defined(__HP_aCC) || defined(__SUNPRO_CC) -#define NATIVE_INT64 -typedef long long Int64; -#endif - -#ifdef NATIVE_INT64 - -#define int64to32(x) ((uint)(x)) -#define int32to64(high,low) ((((Int64)(high))<<32)+(low)) -#define is64plus(x) (x>=0) - -#else - -class Int64 -{ - public: - Int64(); - Int64(uint n); - Int64(uint HighPart,uint LowPart); - -// Int64 operator = (Int64 n); - Int64 operator << (int n); - Int64 operator >> (int n); - - friend Int64 operator / (Int64 n1,Int64 n2); - friend Int64 operator * (Int64 n1,Int64 n2); - friend Int64 operator % (Int64 n1,Int64 n2); - friend Int64 operator + (Int64 n1,Int64 n2); - friend Int64 operator - (Int64 n1,Int64 n2); - friend Int64 operator += (Int64 &n1,Int64 n2); - friend Int64 operator -= (Int64 &n1,Int64 n2); - friend Int64 operator *= (Int64 &n1,Int64 n2); - friend Int64 operator /= (Int64 &n1,Int64 n2); - friend Int64 operator | (Int64 n1,Int64 n2); - friend Int64 operator & (Int64 n1,Int64 n2); - inline friend void operator -= (Int64 &n1,unsigned int n2) - { - if (n1.LowPart (Int64 n1,Int64 n2); - friend bool operator < (Int64 n1,Int64 n2); - friend bool operator != (Int64 n1,Int64 n2); - friend bool operator >= (Int64 n1,Int64 n2); - friend bool operator <= (Int64 n1,Int64 n2); - - void Set(uint HighPart,uint LowPart); - uint GetLowPart() {return(LowPart);} - - uint LowPart; - uint HighPart; -}; - -inline uint int64to32(Int64 n) {return(n.GetLowPart());} -#define int32to64(high,low) (Int64((high),(low))) -#define is64plus(x) ((int)(x).HighPart>=0) - -#endif - -#define INT64ERR int32to64(0x80000000,0) -#define INT64MAX int32to64(0x7fffffff,0) - -void itoa(Int64 n,char *Str); -Int64 atoil(char *Str); - -#endif diff --git a/src/bin/unrar/isnt.cpp b/src/bin/unrar/isnt.cpp deleted file mode 100644 index 493a9eb918..0000000000 --- a/src/bin/unrar/isnt.cpp +++ /dev/null @@ -1,17 +0,0 @@ -#include "rar.hpp" - -#ifdef _WIN_32 -int WinNT() -{ - static int dwPlatformId=-1,dwMajorVersion; - if (dwPlatformId==-1) - { - OSVERSIONINFO WinVer; - WinVer.dwOSVersionInfoSize=sizeof(WinVer); - GetVersionEx(&WinVer); - dwPlatformId=WinVer.dwPlatformId; - dwMajorVersion=WinVer.dwMajorVersion; - } - return(dwPlatformId==VER_PLATFORM_WIN32_NT ? dwMajorVersion:0); -} -#endif diff --git a/src/bin/unrar/isnt.hpp b/src/bin/unrar/isnt.hpp deleted file mode 100644 index 026523614f..0000000000 --- a/src/bin/unrar/isnt.hpp +++ /dev/null @@ -1,6 +0,0 @@ -#ifndef _RAR_ISNT_ -#define _RAR_ISNT_ - -int WinNT(); - -#endif diff --git a/src/bin/unrar/license.txt b/src/bin/unrar/license.txt deleted file mode 100644 index ec35e09a8f..0000000000 --- a/src/bin/unrar/license.txt +++ /dev/null @@ -1,40 +0,0 @@ - ****** ***** ****** UnRAR - free utility for RAR archives - ** ** ** ** ** ** ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - ****** ******* ****** License for use and distribution of - ** ** ** ** ** ** ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ - ** ** ** ** ** ** FREE portable version - ~~~~~~~~~~~~~~~~~~~~~ - - The source code of UnRAR utility is freeware. This means: - - 1. All copyrights to RAR and the utility UnRAR are exclusively - owned by the author - Alexander Roshal. - - 2. The UnRAR sources may be used in any software to handle RAR - archives without limitations free of charge, but cannot be used - to re-create the RAR compression algorithm, which is proprietary. - Distribution of modified UnRAR sources in separate form or as a - part of other software is permitted, provided that it is clearly - stated in the documentation and source comments that the code may - not be used to develop a RAR (WinRAR) compatible archiver. - - 3. The UnRAR utility may be freely distributed. It is allowed - to distribute UnRAR inside of other software packages. - - 4. THE RAR ARCHIVER AND THE UnRAR UTILITY ARE DISTRIBUTED "AS IS". - NO WARRANTY OF ANY KIND IS EXPRESSED OR IMPLIED. YOU USE AT - YOUR OWN RISK. THE AUTHOR WILL NOT BE LIABLE FOR DATA LOSS, - DAMAGES, LOSS OF PROFITS OR ANY OTHER KIND OF LOSS WHILE USING - OR MISUSING THIS SOFTWARE. - - 5. Installing and using the UnRAR utility signifies acceptance of - these terms and conditions of the license. - - 6. If you don't agree with terms of the license you must remove - UnRAR files from your storage devices and cease to use the - utility. - - Thank you for your interest in RAR and UnRAR. - - - Alexander L. Roshal \ No newline at end of file diff --git a/src/bin/unrar/list.cpp b/src/bin/unrar/list.cpp deleted file mode 100644 index d5690064d8..0000000000 --- a/src/bin/unrar/list.cpp +++ /dev/null @@ -1,388 +0,0 @@ -#include "rar.hpp" - -static void ListFileHeader(FileHeader &hd,bool Verbose,bool Technical,bool &TitleShown,bool Bare); -static void ListSymLink(Archive &Arc); -static void ListFileAttr(uint A,int HostOS); -static void ListOldSubHeader(Archive &Arc); -static void ListNewSubHeader(CommandData *Cmd,Archive &Arc,bool Technical); - -void ListArchive(CommandData *Cmd) -{ - Int64 SumPackSize=0,SumUnpSize=0; - uint ArcCount=0,SumFileCount=0; - bool Technical=(Cmd->Command[1]=='T'); - bool Bare=(Cmd->Command[1]=='B'); - bool Verbose=(*Cmd->Command=='V'); - - char ArcName[NM]; - wchar ArcNameW[NM]; - - while (Cmd->GetArcName(ArcName,ArcNameW,sizeof(ArcName))) - { - Archive Arc(Cmd); -#ifdef _WIN_32 - Arc.RemoveSequentialFlag(); -#endif - if (!Arc.WOpen(ArcName,ArcNameW)) - continue; - bool FileMatched=true; - while (1) - { - Int64 TotalPackSize=0,TotalUnpSize=0; - uint FileCount=0; - if (Arc.IsArchive(true)) - { - if (!Arc.IsOpened()) - break; - bool TitleShown=false; - if (!Bare) - { - Arc.ViewComment(); - - // RAR can close a corrupt encrypted archive - if (!Arc.IsOpened()) - break; - - mprintf("\n"); - if (Arc.Solid) - mprintf(St(MListSolid)); - if (Arc.SFXSize>0) - mprintf(St(MListSFX)); - if (Arc.Volume) - if (Arc.Solid) - mprintf(St(MListVol1)); - else - mprintf(St(MListVol2)); - else - if (Arc.Solid) - mprintf(St(MListArc1)); - else - mprintf(St(MListArc2)); - mprintf(" %s\n",Arc.FileName); - if (Technical) - { - if (Arc.Protected) - mprintf(St(MListRecRec)); - if (Arc.Locked) - mprintf(St(MListLock)); - } - } - while(Arc.ReadHeader()>0) - { - int HeaderType=Arc.GetHeaderType(); - if (HeaderType==ENDARC_HEAD) - break; - switch(HeaderType) - { - case FILE_HEAD: - IntToExt(Arc.NewLhd.FileName,Arc.NewLhd.FileName); - if ((FileMatched=Cmd->IsProcessFile(Arc.NewLhd))==true) - { - ListFileHeader(Arc.NewLhd,Verbose,Technical,TitleShown,Bare); - if (!(Arc.NewLhd.Flags & LHD_SPLIT_BEFORE)) - { - TotalUnpSize+=Arc.NewLhd.FullUnpSize; - FileCount++; - } - TotalPackSize+=Arc.NewLhd.FullPackSize; - if (Technical) - ListSymLink(Arc); -#ifndef SFX_MODULE - if (Verbose) - Arc.ViewFileComment(); -#endif - } - break; -#ifndef SFX_MODULE - case SUB_HEAD: - if (Technical && FileMatched && !Bare) - ListOldSubHeader(Arc); - break; -#endif - case NEWSUB_HEAD: - if (FileMatched && !Bare) - { - if (Technical) - ListFileHeader(Arc.SubHead,Verbose,true,TitleShown,false); - ListNewSubHeader(Cmd,Arc,Technical); - } - break; - } - Arc.SeekToNext(); - } - if (!Bare) - if (TitleShown) - { - mprintf("\n"); - for (int I=0;I<79;I++) - mprintf("-"); - char UnpSizeText[20]; - itoa(TotalUnpSize,UnpSizeText); - - char PackSizeText[20]; - itoa(TotalPackSize,PackSizeText); - - mprintf("\n%5lu %16s %8s %3d%%",FileCount,UnpSizeText, - PackSizeText,ToPercentUnlim(TotalPackSize,TotalUnpSize)); - SumFileCount+=FileCount; - SumUnpSize+=TotalUnpSize; - SumPackSize+=TotalPackSize; -#ifndef SFX_MODULE - if (Arc.EndArcHead.Flags & EARC_VOLNUMBER) - { - mprintf(" "); - mprintf(St(MVolumeNumber),Arc.EndArcHead.VolNumber+1); - } -#endif - mprintf("\n"); - } - else - mprintf(St(MListNoFiles)); - - ArcCount++; - -#ifndef NOVOLUME - if (Cmd->VolSize!=0 && ((Arc.NewLhd.Flags & LHD_SPLIT_AFTER) || - Arc.GetHeaderType()==ENDARC_HEAD && - (Arc.EndArcHead.Flags & EARC_NEXT_VOLUME)!=0) && - MergeArchive(Arc,NULL,false,*Cmd->Command)) - { - Arc.Seek(0,SEEK_SET); - } - else -#endif - break; - } - else - { - if (Cmd->ArcNames->ItemsCount()<2 && !Bare) - mprintf(St(MNotRAR),Arc.FileName); - break; - } - } - } - if (ArcCount>1 && !Bare) - { - char UnpSizeText[20],PackSizeText[20]; - itoa(SumUnpSize,UnpSizeText); - itoa(SumPackSize,PackSizeText); - mprintf("\n%5lu %16s %8s %3d%%\n",SumFileCount,UnpSizeText, - PackSizeText,ToPercentUnlim(SumPackSize,SumUnpSize)); - } -} - - -void ListFileHeader(FileHeader &hd,bool Verbose,bool Technical,bool &TitleShown,bool Bare) -{ - if (!Bare) - { - if (!TitleShown) - { - if (Verbose) - mprintf(St(MListPathComm)); - else - mprintf(St(MListName)); - mprintf(St(MListTitle)); - if (Technical) - mprintf(St(MListTechTitle)); - for (int I=0;I<79;I++) - mprintf("-"); - TitleShown=true; - } - - if (hd.HeadType==NEWSUB_HEAD) - mprintf(St(MSubHeadType),hd.FileName); - - mprintf("\n%c",(hd.Flags & LHD_PASSWORD) ? '*' : ' '); - } - - char *Name=hd.FileName; - -#ifdef UNICODE_SUPPORTED - char ConvertedName[NM]; - if ((hd.Flags & LHD_UNICODE)!=0 && *hd.FileNameW!=0 && UnicodeEnabled()) - { - if (WideToChar(hd.FileNameW,ConvertedName) && *ConvertedName!=0) - Name=ConvertedName; - } -#endif - - if (Bare) - { - mprintf("%s\n",Verbose ? Name:PointToName(Name)); - return; - } - - if (Verbose) - mprintf("%s\n%12s ",Name,""); - else - mprintf("%-12s",PointToName(Name)); - - char UnpSizeText[20],PackSizeText[20]; - if (hd.FullUnpSize==INT64MAX) - strcpy(UnpSizeText,"?"); - else - itoa(hd.FullUnpSize,UnpSizeText); - itoa(hd.FullPackSize,PackSizeText); - - mprintf(" %8s %8s ",UnpSizeText,PackSizeText); - - if ((hd.Flags & LHD_SPLIT_BEFORE) && (hd.Flags & LHD_SPLIT_AFTER)) - mprintf(" <->"); - else - if (hd.Flags & LHD_SPLIT_BEFORE) - mprintf(" <--"); - else - if (hd.Flags & LHD_SPLIT_AFTER) - mprintf(" -->"); - else - mprintf("%3d%%",ToPercentUnlim(hd.FullPackSize,hd.FullUnpSize)); - - char DateStr[50]; - hd.mtime.GetText(DateStr,false); - mprintf(" %s ",DateStr); - - if (hd.HeadType==NEWSUB_HEAD) - mprintf(" %c....B ",(hd.SubFlags & SUBHEAD_FLAGS_INHERITED) ? 'I' : '.'); - else - ListFileAttr(hd.FileAttr,hd.HostOS); - - mprintf(" %8.8X",hd.FileCRC); - mprintf(" m%d",hd.Method-0x30); - if ((hd.Flags & LHD_WINDOWMASK)<=6*32) - mprintf("%c",((hd.Flags&LHD_WINDOWMASK)>>5)+'a'); - else - mprintf(" "); - mprintf(" %d.%d",hd.UnpVer/10,hd.UnpVer%10); - - static const char *RarOS[]={ - "DOS","OS/2","Win95/NT","Unix","MacOS","BeOS","WinCE","","","" - }; - - if (Technical) - mprintf("\n%22s %8s %4s", - (hd.HostOS",FileName); - } -} - - -void ListFileAttr(uint A,int HostOS) -{ - switch(HostOS) - { - case HOST_MSDOS: - case HOST_OS2: - case HOST_WIN32: - case HOST_MACOS: - mprintf(" %c%c%c%c%c%c%c ", - (A & 0x08) ? 'V' : '.', - (A & 0x10) ? 'D' : '.', - (A & 0x01) ? 'R' : '.', - (A & 0x02) ? 'H' : '.', - (A & 0x04) ? 'S' : '.', - (A & 0x20) ? 'A' : '.', - (A & 0x800) ? 'C' : '.'); - break; - case HOST_UNIX: - case HOST_BEOS: - switch (A & 0xF000) - { - case 0x4000: - mprintf("d"); - break; - case 0xA000: - mprintf("l"); - break; - default: - mprintf("-"); - break; - } - mprintf("%c%c%c%c%c%c%c%c%c", - (A & 0x0100) ? 'r' : '-', - (A & 0x0080) ? 'w' : '-', - (A & 0x0040) ? ((A & 0x0800) ? 's':'x'):((A & 0x0800) ? 'S':'-'), - (A & 0x0020) ? 'r' : '-', - (A & 0x0010) ? 'w' : '-', - (A & 0x0008) ? ((A & 0x0400) ? 's':'x'):((A & 0x0400) ? 'S':'-'), - (A & 0x0004) ? 'r' : '-', - (A & 0x0002) ? 'w' : '-', - (A & 0x0001) ? 'x' : '-'); - break; - } -} - - -#ifndef SFX_MODULE -void ListOldSubHeader(Archive &Arc) -{ - switch(Arc.SubBlockHead.SubType) - { - case EA_HEAD: - mprintf(St(MListEAHead)); - break; - case UO_HEAD: - mprintf(St(MListUOHead),Arc.UOHead.OwnerName,Arc.UOHead.GroupName); - break; - case MAC_HEAD: - mprintf(St(MListMACHead1),Arc.MACHead.fileType>>24,Arc.MACHead.fileType>>16,Arc.MACHead.fileType>>8,Arc.MACHead.fileType); - mprintf(St(MListMACHead2),Arc.MACHead.fileCreator>>24,Arc.MACHead.fileCreator>>16,Arc.MACHead.fileCreator>>8,Arc.MACHead.fileCreator); - break; - case BEEA_HEAD: - mprintf(St(MListBeEAHead)); - break; - case NTACL_HEAD: - mprintf(St(MListNTACLHead)); - break; - case STREAM_HEAD: - mprintf(St(MListStrmHead),Arc.StreamHead.StreamName); - break; - default: - mprintf(St(MListUnkHead),Arc.SubBlockHead.SubType); - break; - } -} -#endif - - -void ListNewSubHeader(CommandData *Cmd,Archive &Arc,bool Technical) -{ - if (Arc.SubHead.CmpName(SUBHEAD_TYPE_CMT) && - (Arc.SubHead.Flags & LHD_SPLIT_BEFORE)==0 && !Cmd->DisableComment) - { - Array CmtData; - int ReadSize=Arc.ReadCommentData(&CmtData,NULL); - if (ReadSize!=0) - { - mprintf(St(MFileComment)); - OutComment((char *)&CmtData[0],ReadSize); - } - } - if (Arc.SubHead.CmpName(SUBHEAD_TYPE_STREAM) && - (Arc.SubHead.Flags & LHD_SPLIT_BEFORE)==0) - { - int DestSize=Arc.SubHead.SubData.Size()/2; - wchar DestNameW[NM]; - char DestName[NM]; - if (DestSize - - " -#define MUNRARTitle1 "\nUsage: unrar - - " -#define MRARTitle2 "\n <@listfiles...> " -#define MCHelpCmd "\n\n" -#define MCHelpCmdA "\n a Add files to archive" -#define MCHelpCmdC "\n c Add archive comment" -#define MCHelpCmdCF "\n cf Add files comment" -#define MCHelpCmdCH "\n ch Change archive parameters" -#define MCHelpCmdCW "\n cw Write archive comment to file" -#define MCHelpCmdD "\n d Delete files from archive" -#define MCHelpCmdE "\n e Extract files to current directory" -#define MCHelpCmdF "\n f Freshen files in archive" -#define MCHelpCmdI "\n i[par]= Find string in archives" -#define MCHelpCmdK "\n k Lock archive" -#define MCHelpCmdL "\n l[t,b] List archive [technical, bare]" -#define MCHelpCmdM "\n m[f] Move to archive [files only]" -#define MCHelpCmdP "\n p Print file to stdout" -#define MCHelpCmdR "\n r Repair archive" -#define MCHelpCmdRC "\n rc Reconstruct missing volumes" -#define MCHelpCmdRN "\n rn Rename archived files" -#define MCHelpCmdRR "\n rr[N] Add data recovery record" -#define MCHelpCmdRV "\n rv[N] Create recovery volumes" -#define MCHelpCmdS "\n s[name|-] Convert archive to or from SFX" -#define MCHelpCmdT "\n t Test archive files" -#define MCHelpCmdU "\n u Update files in archive" -#define MCHelpCmdV "\n v[t,b] Verbosely list archive [technical,bare]" -#define MCHelpCmdX "\n x Extract files with full path" -#define MCHelpSw "\n\n" -#define MCHelpSwm "\n - Stop switches scanning" -#define MCHelpSwAC "\n ac Clear Archive attribute after compression or extraction" -#define MCHelpSwAD "\n ad Append archive name to destination path" -#define MCHelpSwAG "\n ag[format] Generate archive name using the current date" -#define MCHelpSwAO "\n ao Add files with Archive attribute set" -#define MCHelpSwAP "\n ap Set path inside archive" -#define MCHelpSwAS "\n as Synchronize archive contents" -#define MCHelpSwAV "\n av Put authenticity verification (registered versions only)" -#define MCHelpSwAVm "\n av- Disable authenticity verification check" -#define MCHelpSwCm "\n c- Disable comments show" -#define MCHelpSwCFGm "\n cfg- Disable read configuration" -#define MCHelpSwCL "\n cl Convert names to lower case" -#define MCHelpSwCU "\n cu Convert names to upper case" -#define MCHelpSwDF "\n df Delete files after archiving" -#define MCHelpSwDH "\n dh Open shared files" -#define MCHelpSwDS "\n ds Disable name sort for solid archive" -#define MCHelpSwEa "\n e[+] Set file exclude and include attributes" -#define MCHelpSwED "\n ed Do not add empty directories" -#define MCHelpSwEE "\n ee Do not save and extract extended attributes" -#define MCHelpSwEN "\n en Do not put 'end of archive' block" -#define MCHelpSwEP "\n ep Exclude paths from names" -#define MCHelpSwEP1 "\n ep1 Exclude base directory from names" -#define MCHelpSwEP2 "\n ep2 Expand paths to full" -#define MCHelpSwEP3 "\n ep3 Expand paths to full including the drive letter" -#define MCHelpSwF "\n f Freshen files" -#define MCHelpSwHP "\n hp[password] Encrypt both file data and headers" -#define MCHelpSwIDP "\n id[c,d,p,q] Disable messages" -#define MCHelpSwIEML "\n ieml[addr] Send archive by email" -#define MCHelpSwIERR "\n ierr Send all messages to stderr" -#define MCHelpSwILOG "\n ilog[name] Log errors to file (registered versions only)" -#define MCHelpSwINUL "\n inul Disable all messages" -#define MCHelpSwIOFF "\n ioff Turn PC off after completing an operation" -#define MCHelpSwISND "\n isnd Enable sound" -#define MCHelpSwK "\n k Lock archive" -#define MCHelpSwKB "\n kb Keep broken extracted files" -#define MCHelpSwMn "\n m<0..5> Set compression level (0-store...3-default...5-maximal)" -#define MCHelpSwMC "\n mc Set advanced compression parameters" -#define MCHelpSwMD "\n md Dictionary size in KB (64,128,256,512,1024,2048,4096 or A-G)" -#define MCHelpSwMS "\n ms[ext;ext] Specify file types to store" -#define MCHelpSwMT "\n mt Set the number of threads" -#define MCHelpSwN "\n n Include only specified file" -#define MCHelpSwNa "\n n@ Read file names to include from stdin" -#define MCHelpSwNal "\n n@ Include files in specified list file" -#define MCHelpSwOp "\n o+ Overwrite existing files" -#define MCHelpSwOm "\n o- Do not overwrite existing files" -#define MCHelpSwOC "\n oc Set NTFS Compressed attribute" -#define MCHelpSwOL "\n ol Save symbolic links as the link instead of the file" -#define MCHelpSwOR "\n or Rename files automatically" -#define MCHelpSwOS "\n os Save NTFS streams" -#define MCHelpSwOW "\n ow Save or restore file owner and group" -#define MCHelpSwP "\n p[password] Set password" -#define MCHelpSwPm "\n p- Do not query password" -#define MCHelpSwR "\n r Recurse subdirectories" -#define MCHelpSwR0 "\n r0 Recurse subdirectories for wildcard names only" -#define MCHelpSwRI "\n ri

[:] Set priority (0-default,1-min..15-max) and sleep time in ms" -#define MCHelpSwRR "\n rr[N] Add data recovery record" -#define MCHelpSwRV "\n rv[N] Create recovery volumes" -#define MCHelpSwS "\n s[,v[-],e] Create solid archive" -#define MCHelpSwSm "\n s- Disable solid archiving" -#define MCHelpSwSC "\n sc[obj] Specify the character set" -#define MCHelpSwSFX "\n sfx[name] Create SFX archive" -#define MCHelpSwSI "\n si[name] Read data from standard input (stdin)" -#define MCHelpSwSL "\n sl Process files with size less than specified" -#define MCHelpSwSM "\n sm Process files with size more than specified" -#define MCHelpSwT "\n t Test files after archiving" -#define MCHelpSwTK "\n tk Keep original archive time" -#define MCHelpSwTL "\n tl Set archive time to latest file" -#define MCHelpSwTN "\n tn