mplpl / unrar_amiga

Port of unrar for MorphOS, AmigaOS and AROS
Other
6 stars 2 forks source link

unrar fails with guru during unpacking of multivolume archive #22

Closed mplpl closed 4 years ago

mplpl commented 4 years ago

Unpacking multivolume archive fails in the following situation: 1) the archive is using rar compression version <5 (may be created in rar3 or rar4 but also in rar5 if -ma4 option was used 2) some of the volumes are missing

The issue does NOT occur when all the volumes are available or when rar5 compression is used.

The issue has been observed on AmigaOS4. Later on it was confirmed also on MorphOS, AmigaOS3 and AROS.

It impacts unrar 5.70 and 5.80.

mplpl commented 4 years ago

This issue also happening when calling "unrar lta -v" for archives like in this ticket description.

mplpl commented 4 years ago

Dump from AmigaOS 4.1

Dump of context at 0xC7E937C0
Trap type: DSI exception
Machine State (raw): 0x0000F070
Machine State (verbose): [ExtInt on] [User] [FPU on] [IAT on] [DAT on] 
Temporary stack trace:
#0: in module Kickstart/kernel+0x00021604 (0x08821604)
#1: in module Kickstart/newlib.library.kmod+0x0000BA18 (0x08BCA098)
#2: 0x1F575944
#3: 0x1F582D40
#4: 0x1F57CE1C
#5: 0x1F57E314
#6: 0x1F5789D0
#7: 0x1F579164
#8: 0x1F5AA280
#9: 0x1F5AC218
#10: 0x1F5921AC
#11: 0x1F5939A0
#12: 0x1F5A37C0
#13: 0x1F5704F4
#14: in module Kickstart/newlib.library.kmod+0x000020A4 (0x08BC0724)
#15: in module Kickstart/newlib.library.kmod+0x00002D0C (0x08BC138C)
#16: in module Kickstart/newlib.library.kmod+0x00002EE8 (0x08BC1568)
#17: 0x1F570190
#18: in module Kickstart/dos.library.kmod+0x000255C8 (0x089EB508)
#19: in module Kickstart/kernel+0x00045A64 (0x08845A64)
#20: in module Kickstart/kernel+0x00045AAC (0x08845AAC)
#21: 0x00000000

Crashed process: unrarsrc/unrar (0x3E6B2020)
 0: 08BCA098 3C5BC000 836E9F81 090BDDCC 3D900DB4 00000000 090BDDCC 1F575944
 8: FFFFFFFF 08821604 3E6B2020 08821FE4 00000164 3C743800 3C61EA54 3C61EA44
16: 3C71A008 00000005 3C60E868 00000000 08000000 3C61EA14 3C603C18 00000001
24: 3C5FA688 3C72A008 00000020 09270000 3D900DB4 091C1B82 3D900DB4 090BDDCC
CR: 33953953   XER: CFCFCFCF  CTR: 08821604  LR: 08823850
DSISR: 42000000  DAR: 3C5BBFF0
DSI verbose error description: Access not found in hash or BAT (page fault)
Access was a store operation

Kernel command line: NoRamPager

Registers pointing to code:
r0 : native kernel module Kickstart/newlib.library.kmod+0x0000ba18
r3 : native kernel module Kickstart/kernel+0x008bddcc
r6 : native kernel module Kickstart/kernel+0x008bddcc
r7 : unrarsrc/unrar:_ZN5ArrayIhE3AddEj()+0xd4 (section 1 @ 0x5920)
r9 : native kernel module Kickstart/kernel+0x00021604
r11: native kernel module Kickstart/kernel+0x00021fe4
r13: unrarsrc/unrar:_ZZ7GetWidePKcE8StrTable()+0x7e2c (section 20 @ 0x7E2C)
r14: module unrarsrc/unrar at 0x3C61EA54 (section 6 @ 0xA30)
r15: module unrarsrc/unrar at 0x3C61EA44 (section 6 @ 0xA20)
r21: module unrarsrc/unrar at 0x3C61EA14 (section 6 @ 0x9F0)
r23: module unrarsrc/unrar at 0x00000001 (section 0 @ 0xFFFFFFDC)
r27: native kernel module Kickstart/mounter.library+0x006bd4e0
r29: native kernel module Kickstart/kernel+0x009c1b82
r31: native kernel module Kickstart/kernel+0x008bddcc
ip : native kernel module Kickstart/kernel+0x00021604
lr : native kernel module Kickstart/kernel+0x00023850
ctr: native kernel module Kickstart/kernel+0x00021604

Stack trace:
(0x3C5BC000) native kernel module Kickstart/kernel+0x00021604
(0x3C5BC030) native kernel module Kickstart/kernel+0x00023850
(0x3C5BC050) unrarsrc/unrar:_ZN5ArrayIhE3AddEj()+0xd4 (section 1 @ 0x5920)
(0x3C5BC070) unrarsrc/unrar:_ZN7RawRead4ReadEj()+0x124 (section 1 @ 0x12D1C)
(0x3C5BC090) unrarsrc/unrar:_ZN7Archive12ReadHeader15Ev()+0x264 (section 1 @ 0xCDF8)
(0x3C5BE2E0) unrarsrc/unrar:_ZN7Archive10ReadHeaderEv()+0xf4 (section 1 @ 0xE2F0)
(0x3C5BE2F0) unrarsrc/unrar:_ZN7Archive9IsArchiveEb()+0x2a8 (section 1 @ 0x89AC)
(0x3C5BE4B0) unrarsrc/unrar:_ZN7Archive10WCheckOpenEPKw()+0x7c (section 1 @ 0x9140)
(0x3C5BE4D0) unrarsrc/unrar:_ZN11RecVolumes37RestoreEP10RAROptionsPKwb()+0x1e0 (section 1 @ 0x3A25C)
(0x3C5E82B0) unrarsrc/unrar:_Z17RecVolumesRestoreP10RAROptionsPKwb()+0x3e0 (section 1 @ 0x3C1F4)
(0x3C5F8680) unrarsrc/unrar:_Z12MergeArchiveR7ArchiveP11ComprDataIObw()+0x380 (section 1 @ 0x22188)
(0x3C5FC6F0) unrarsrc/unrar:_Z11ListArchiveP11CommandData()+0x6d8 (section 1 @ 0x2397C)
(0x3C60E820) unrarsrc/unrar:_ZN11CommandData14ProcessCommandEv()+0x3d8 (section 1 @ 0x3379C)
(0x3C61DBC0) unrarsrc/unrar:main()+0x2e4 (section 1 @ 0x4D0)
(0x3C61DD00) native kernel module Kickstart/newlib.library.kmod+0x000020a4
(0x3C61DD70) native kernel module Kickstart/newlib.library.kmod+0x00002d0c
(0x3C61DF10) native kernel module Kickstart/newlib.library.kmod+0x00002ee8
(0x3C61DF50) unrarsrc/unrar:_start()+0x170 (section 1 @ 0x16C)
(0x3C61DF90) native kernel module Kickstart/dos.library.kmod+0x000255c8
(0x3C61DFC0) native kernel module Kickstart/kernel+0x00045a64
(0x3C61DFD0) native kernel module Kickstart/kernel+0x00045aac

Disassembly of crash site:
 088215F4: 4E800421   bctrl             
 088215F8: 4BFFFF44   b                 0x882153C
 088215FC: 38600000   li                r3,0
 08821600: 4E800020   blr               
>08821604: 9421FFF0   stwu              r1,-16(r1)
 08821608: 7C0802A6   mflr              r0
 0882160C: 93E1000C   stw               r31,12(r1)
 08821610: 90010014   stw               r0,20(r1)
 08821614: 83E30010   lwz               r31,16(r3)
 08821618: 893F0127   lbz               r9,295(r31)
Stack pointer (0x3C5BC000) is outside bounds
Redzone is damaged (3)

68k register dump
DATA: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 00000000
ADDR: 00000000 00000000 00000000 00000000 00000000 00000000 00000000 3C5BDFF0
Page information:
Page 0xC7EF2450:
Virtual Address: 0x3C5BB000
Physical Address: 0x00000000
Lock count: 0
Flags (0x800): (Guard) 
Protection bits (0x0): (super state only) 
Page is assigned to VMArea primary heap
mplpl commented 4 years ago

The issue is caused by running out of stack space. It is set by default to 400000 bytes.

Workaround 1: before calling unrar, set stack to 800000 bytes using command: stack 800000 Unfortunately, this cannot be applied on MorphOS.

Workaround 2: get all the volumes - without them, even if unrar does not crash, it will exit with an error.

mplpl commented 4 years ago

Full explanation.

In case when multivolume rar archive with some volumes missing is given to unrar, it tries to recover missing volumes. For that purpose special recovery volumes need to be created using "rar -rc" command. It works a bit like RAID5/6 mirroring: if you have one recovery volume create, any of volumes can be broken and it will still be possible to unpack such archive. If you have 2 recovery volumes created, any two can fail and so on. So, if there are no recovery volumes (which is what happens in the case described in this issue) and some volumes are missing, it will still start the recovery only to learn about missing volumes. Then it would exit with error. But starting recovery creates some classes that consume significant about of stack, in particular in case of archives with compression version <5 (handled by RecVol3.cpp). And so it overflows the stack and crashed the process.

In the next version of unrar, I will increase a default stack size.

mplpl commented 4 years ago

Resolved by commit https://github.com/mplpl/unrar_amiga/commit/3682131eaab68e74631d0167796d299420bdc2f5 in 5.90.