├── .github └── workflows │ └── codacy.yml ├── .gitignore ├── .gitmodules ├── AutoInstall ├── Avalanche.guide ├── Avalanche.guide.info ├── Avalanche.info ├── AvalanchePPC.info ├── Install ├── Install.info ├── LICENSE ├── README.md ├── avalanche.readme ├── avalanche.readme.info ├── catalogs ├── avalanche.cd ├── avalanche.cs └── avalanche.ct ├── libs └── xvs.l.main └── src ├── Avalanche_rev.h ├── Avalanche_rev.i ├── Avalanche_rev.rev ├── Avalanche_rev.s ├── Makefile ├── arexx.c ├── arexx.h ├── avalanche.c ├── avalanche.h ├── config.c ├── config.h ├── deark.c ├── deark.h ├── http.c ├── http.h ├── libs.c ├── libs.h ├── locale.c ├── locale.h ├── locale_strings.h ├── misc.c ├── misc.h ├── mod_lha.c ├── mod_zip.c ├── module.c ├── module.h ├── new.c ├── new.h ├── os3 └── Makefile ├── os4 ├── Makefile └── Makefile.gcc ├── req.c ├── req.h ├── win.c ├── win.h ├── xad.c ├── xad.h ├── xfd.c ├── xfd.h ├── xvs.c └── xvs.h /.github/workflows/codacy.yml: -------------------------------------------------------------------------------- 1 | # This workflow uses actions that are not certified by GitHub. 2 | # They are provided by a third-party and are governed by 3 | # separate terms of service, privacy policy, and support 4 | # documentation. 5 | 6 | # This workflow checks out code, performs a Codacy security scan 7 | # and integrates the results with the 8 | # GitHub Advanced Security code scanning feature. For more information on 9 | # the Codacy security scan action usage and parameters, see 10 | # https://github.com/codacy/codacy-analysis-cli-action. 11 | # For more information on Codacy Analysis CLI in general, see 12 | # https://github.com/codacy/codacy-analysis-cli. 13 | 14 | name: Codacy Security Scan 15 | 16 | on: 17 | push: 18 | branches: [ "main" ] 19 | pull_request: 20 | # The branches below must be a subset of the branches above 21 | branches: [ "main" ] 22 | schedule: 23 | - cron: '38 18 * * 5' 24 | 25 | permissions: 26 | contents: read 27 | 28 | jobs: 29 | codacy-security-scan: 30 | permissions: 31 | contents: read # for actions/checkout to fetch code 32 | security-events: write # for github/codeql-action/upload-sarif to upload SARIF results 33 | actions: read # only required for a private repository by github/codeql-action/upload-sarif to get the Action run status 34 | name: Codacy Security Scan 35 | runs-on: ubuntu-latest 36 | steps: 37 | # Checkout the repository to the GitHub Actions runner 38 | - name: Checkout code 39 | uses: actions/checkout@v3 40 | 41 | # Execute Codacy Analysis CLI and generate a SARIF output with the security issues identified during the analysis 42 | - name: Run Codacy Analysis CLI 43 | uses: codacy/codacy-analysis-cli-action@d840f886c4bd4edc059706d09c6a1586111c540b 44 | with: 45 | # Check https://github.com/codacy/codacy-analysis-cli#project-token to get your project token from your Codacy repository 46 | # You can also omit the token and run the tools that support default configurations 47 | project-token: ${{ secrets.CODACY_PROJECT_TOKEN }} 48 | verbose: true 49 | output: results.sarif 50 | format: sarif 51 | # Adjust severity of non-security issues 52 | gh-code-scanning-compat: true 53 | # Force 0 exit code to allow SARIF file generation 54 | # This will handover control about PR rejection to the GitHub side 55 | max-allowed-issues: 2147483647 56 | 57 | # Upload the SARIF file generated in the previous step 58 | - name: Upload SARIF results file 59 | uses: github/codeql-action/upload-sarif@v2 60 | with: 61 | sarif_file: results.sarif 62 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Prerequisites 2 | *.d 3 | 4 | # Object files 5 | *.o 6 | *.ko 7 | *.obj 8 | *.elf 9 | 10 | # Linker output 11 | *.ilk 12 | *.map 13 | *.exp 14 | 15 | # Precompiled Headers 16 | *.gch 17 | *.pch 18 | 19 | # Libraries 20 | *.lib 21 | *.a 22 | *.la 23 | *.lo 24 | 25 | # Shared objects (inc. Windows DLLs) 26 | *.dll 27 | *.so 28 | *.so.* 29 | *.dylib 30 | 31 | # Executables 32 | *.exe 33 | *.out 34 | *.app 35 | *.i*86 36 | *.x86_64 37 | *.hex 38 | 39 | # Debug files 40 | *.dSYM/ 41 | *.su 42 | *.idb 43 | *.pdb 44 | 45 | # Kernel Module Compile Results 46 | *.mod* 47 | *.cmd 48 | .tmp_versions/ 49 | modules.order 50 | Module.symvers 51 | Mkfile.old 52 | dkms.conf 53 | 54 | # Avalanche 55 | Avalanche 56 | AvalanchePPC 57 | avalanche.lha 58 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/chris-y/avalanche/d32bc64424e88d857c8db56bfef035dfc7af7316/.gitmodules -------------------------------------------------------------------------------- /AutoInstall: -------------------------------------------------------------------------------- 1 | .bra { 2 | .ket } 3 | 4 | CopyStore Avalanche/AvalanchePPC ${AppDir/AvalanchePPC} 5 | -------------------------------------------------------------------------------- /Avalanche.guide: -------------------------------------------------------------------------------- 1 | @database "Avalanche.guide" 2 | @wordwrap 3 | 4 | @node Main "Avalanche" 5 | @{b}Avalanche@{ub} 6 | 7 | @{"Introduction " link intro} 8 | @{"Installation " link install} 9 | @{"Configuration" link config} 10 | @{"Usage " link usage} 11 | @{"ARexx port " link arexx} 12 | @{"Translations " link locale} 13 | @{"Changelog " link history} 14 | @{"Contact " link contact} 15 | @endnode 16 | 17 | @node intro "Introduction" 18 | This is a simple ReAction based GUI for xadmaster.library. 19 | 20 | It was written as everything similar on Aminet appears to require MUI, and the ones included with the OS over the years are not freely distributable. AmigaOS 3.2 does not include such a tool, so Avalanche was born out of boredom of opening a shell and typing "lha x archive.lha". 21 | 22 | It has since been extended to also support decrunching with xfdmaster.library, scanning extracted files with xvs.library, and basic editing/creation of LhA and Zip archives. 23 | 24 | @endnode 25 | 26 | @node install "Installation" 27 | Please use the included Installer script. 28 | 29 | If you must install manually, you can copy the program anywhere on your hard drive. 30 | The install script additionally modifies the default tool for "archive" type files to be Avalanche. In a standard install of OS3.2 this is used for all subtypes. 31 | 32 | @endnode 33 | 34 | @node config "Configuration" 35 | Configuration is done via ToolTypes or through the equivalent options in the GUI. Currently the following ToolTypes are recognised: 36 | 37 | @{b}SOURCEDIR@{ub} Initial drawer to show in ASL requester (default = RAM:) 38 | @{b}DEST@{ub} Destination to extract the archive to (default = RAM:) 39 | @{b}TMPDIR@{ub} Path for temporary directory (default = T:) 40 | @{b}VIEWMODE@{ub} LIST or BROWSER (default = BROWSER) 41 | @{b}IGNOREFS@{ub} Enables the "Ignore filesystems" option 42 | @{b}WINX@{ub}/@{b}WINY@{ub}/@{b}WINW@{ub}/@{b}WINH@{ub} Window position/width/height 43 | @{b}PROGRESSSIZE@{ub} Size of progress bar (0-100) at window open 44 | @{b}VIRUSSCAN@{ub} Use xvs.library to @{"scan files" link vscan} after extraction 45 | @{b}CLOSE@{ub} Action to take when last window closed ASK|HIDE|QUIT (default = ASK) 46 | @{b}NOASLHOOK@{ub} Disables the ASL filter so it shows all files 47 | @{b}DRAGLOCK@{ub} Prevent adding files with drag'n'drop 48 | @{b}AISS@{ub} Use AISS images (intended for OS4, probably won't work correctly on OS3.2) 49 | @{b}MODULES@{ub} Select which modules to enable (XAD|XFD|DEARK) (default = XAD|XFD) 50 | @{b}CX_POPUP@{ub} Whether to open the window on startup 51 | @{b}CX_PRIORITY@{ub} Commodities priority 52 | @{b}CX_POPKEY@{ub} Hotkey to show the window if hidden (default = ctrl alt a) 53 | @endnode 54 | 55 | @node usage "Usage" 56 | Avalanche can be started as a default tool for an archive, or manually. If started manually an archive can be selected using the button next to Archive, or by dragging it into the window. Do not drop the file into a highlighted file list area, as this will add the archive to the one currently being viewed (see @{"editing" link editing}), rather than opening it. 57 | 58 | It is possible to "quick extract" archives into their current directory by highlighting 59 | and selecting "Extract here" from the Tools menu. 60 | 61 | When a valid archive or crunched file is loaded, the contents will be displayed. Unchecked items will not be extracted. 62 | 63 | The state of checkboxes can be toggled by clicking on them, or by choosing "Select all" or "Clear selection" from the Edit menu. Note that this will act on everything in the current and subdirectories when in the browser mode. 64 | 65 | Clicking Extract will extract the archive to the chosen destination. If @{"scan for viruses" link config} is enabled then Avalanche will scan each file using xvs.library after extraction. Any infected files will be deleted. See @{"virus scanning" link vscan} for more details. 66 | 67 | The option to "Ignore filesystems" is only useful for DMS and similar disk archives. Normally Avalanche will check for a valid filesystem, and list the individual files. With this option set, the raw disk image will be listed instead. 68 | 69 | If an Lha or Zip archive is loaded, basic editing is enabled, see @{"editing" link editing} for details. These can also be created by selecting "New archive" from the Project menu. 70 | 71 | @{b}Limitations@{ub}: 72 | * Mixed file/disk archives are not supported. 73 | * Disk images containing multiple filesystems are not currently supported. 74 | * Encrypted archives are not fully supported. 75 | * xadmaster.library v12 has some bugs relating to certain LhA archives. 76 | The fix is to use v13 - there is an experimental build for 68k at https://github.com/Hagbard-Celin/xadmaster_Amiga_68k 77 | 78 | @endnode 79 | 80 | @node editing "Editing" 81 | If an LhA or Zip archive is loaded, it is possible to do basic editing. Note that currently Zip editing needs zip.library and therefore is only available on OS4. LhA requires the LhA command line tool. 82 | 83 | In the Edit menu the following new items are available: 84 | 85 | @{u}Add files@{uu} 86 | This opens an ASL requester to select files to add to the archive. They will be added to the root directory (or the currently displayed directory for Zip archives if in browser mode). Directories are currently ignored - any tree structure will be flattened. 87 | 88 | It is also possible to add files by dragging into the file list - the area will be highlighted to indicate that files will be added. 89 | 90 | @{u}Delete selected items@{uu} 91 | This deletes the currently selected items from the archive. Note that this does not cascade into subdirectories, it only deletes the displayed files. 92 | 93 | In the Project menu it is possible to create a new archive. This displays another window to select a filename and type. When the archive is created it is displayed. A default file is added as empty archives are not supported. 94 | @endnode 95 | 96 | @node vscan "Virus scanning" 97 | Avalanche can use xvs.library to scan files for viruses on extraction and addition. 98 | xvs.library can be downloaded from https://www.vht-dk.dk/ 99 | 100 | Limitations: 101 | Due to the way xvs.library works, files which do not completely fit into memory cannot be scanned. 102 | Only Amiga viruses will be detected. 103 | On OS4 the file xvs.l.main (included with Avalanche) needs to be copied to libs: alongside the main library (the install script will do this if xvs.library is installed already). 104 | Infected files will be deleted without warning. 105 | Files will not be further extracted in order to be scanned, so infected files that are individually compressed inside the archive will not be picked up. It is recommended to run a scan with a full featured virus checker over any archives of concern. 106 | @endnode 107 | 108 | @node deark "Deark" 109 | Deark is a program which can extract all sorts of data from files, and convert obscure file formats to more modern ones. 110 | 111 | Download from Aminet, source is at https://github.com/jsummers/deark 112 | 113 | To use in Avalanche it needs to be present in the path, and enabled in the MODULES @{"tooltype" link config}. 114 | 115 | There is a bug which prevents extraction to root directories on the Amiga, so currently extraction needs to be to a subdirectory. 116 | 117 | The 68k version appears to be very unstable. 118 | 119 | @endnode 120 | 121 | @node arexx "ARexx port" 122 | Avalanche has an ARexx port called "AVALANCHE". 123 | This is mostly for internal use, but has the following commands: 124 | 125 | @{b}OPEN@{ub} FILE/A 126 | - Open FILE in a new window 127 | @{b}SHOW@{ub} 128 | - Show Avalanche or bring window to front 129 | @{b}VERSION@{ub} 130 | - returns the current version number in RESULT 131 | 132 | @endnode 133 | 134 | @node history "Changelog" 135 | @rem keep this to <80 chars for readme 136 | @{u}2.4 (22.09.2023)@{uu} 137 | * Support @{"Deark" link deark} (needs enabling by tooltype - see below) 138 | This is a "beta" feature, it may be unstable and due to a bug in 139 | Deark, it is not possible to extract to the root of any device. 140 | * Add option to select modules (MODULES @{"tooltype" link config}) 141 | * Fix password caching 142 | * Also use T: as temp by default from CLI 143 | 144 | @{u}2.3 (16.06.2023)@{uu} 145 | * Fix setting of list mode 146 | * Remove tree in list mode view 147 | 148 | @{u}2.2 (09.05.2023)@{uu} 149 | * Visual improvements 150 | * Added ability to use AISS images (on OS4) 151 | * Added option to check for updates 152 | * Fix the display of current settings in the prefs window 153 | * Fix snapshot position and add a warning 154 | * Fixed some Enforcer hits 155 | 156 | @{u}2.1 (29.03.2023)@{uu} 157 | * New browser mode, removed old hierarchical browser. 158 | * Select/Clear/Invert selection now act on the current directory and 159 | all subdirectories when in the new browser mode. 160 | * Basic editing of (LhA, Zip) archives (Zip needs zip.library - OS4 only) 161 | * Create new (LhA, Zip) archives 162 | 163 | @{u}1.11 (11.02.2023)@{uu} 164 | * Improve window handling 165 | - Can now open new window from the GUI 166 | - Can select to ask/hide/quit when last window closed 167 | (NB: CONFIRMQUIT tooltype no longer used) 168 | * Can now specify an archive on the command line 169 | 170 | @{u}1.10 (12.01.2023)@{uu} 171 | * Dragging a drawer into the window now sets the source directory, if 172 | an archive hasn't already been opened. 173 | * Fixed some problems opening archives in certain circumstances. 174 | * OS4 build now uses newlib. 175 | 176 | @{u}1.9 (21.12.2022)@{uu} 177 | * Add "snapshot window" option 178 | - note that the position is not saved unless save is clicked in prefs 179 | * Add ToolType to disable the ASL hook (filters ASL req to only show archives) 180 | * Add ToolType to set the initial drawer visible in ASL requester 181 | * Fix iconify 182 | * Rebuilt with optimisations 183 | 184 | @{u}1.8 (07.12.2022)@{uu} 185 | * Multiple windows supported internally. Limitations: 186 | - Commodities events only operate on the main (first) window 187 | - Does not spawn new process, so cannot use other windows whilst one is busy 188 | * Simple @{"ARexx port" link arexx} added. 189 | * Config options moved to separate prefs window 190 | - Note the options to snapshot the current window and change the default 191 | destination are currently not available. They can still be manually set 192 | through @{"tooltypes" link config}. 193 | 194 | @{u}1.7 (03.08.2022)@{uu} 195 | * Avalanche now registers as a commodity 196 | * Added Tools menu item "Extract here" for quick extraction 197 | * Fix initial state of "confirm quit" and "ignore fs" menu items. 198 | 199 | @{u}1.6 (31.05.2022)@{uu} 200 | * Add ability to extract disk archives to images 201 | * Add ability to extract files from disk images/archives 202 | * Double-clicking now extracts the clicked file to a temporary location and opens it. 203 | NB: This has required the previous "single click to select/deselect" to be disabled, 204 | as the functionality was incompatible. 205 | * Add option to enable/disable the quit confirmation requester 206 | * Localisaton support 207 | * Improved progress display - now shows current file progress and total 208 | * Fix loading/saving of virusscan pref on OS4 209 | * Fix unchecking of files in archive 210 | 211 | @{u}1.5 (25.03.2022)@{uu} 212 | * Add option to use xvs.library to scan the extracted files for viruses 213 | * Fallback to xfdmaster.library if file not recognised 214 | * Support encrypted archive entries 215 | * Installer no longer overwrites existing icon on update 216 | * Add Archive Info menu option - currently shows the filetype only 217 | 218 | @{u}1.4 (16.03.2022)@{uu} 219 | * Now includes OS4 native build 220 | * Allow abort during extraction (button or ESC) 221 | * Now asks whether to overwrite files 222 | * ESC can now be used to quit, and Enter to start extraction 223 | * List of files can now be sorted by clicking on the column header 224 | * Clicking anywhere on the line now toggles the checkbox 225 | * Now confirms quit 226 | * Added option to invert selection to menu 227 | * Striped listbrowser 228 | 229 | @{u}1.3 (21.01.2022)@{uu} 230 | * Due to a last minute error handling change, v1.2 won't extract many archives, oops. 231 | * Added ability to drag or extended select more than one file 232 | 233 | @{u}1.2 (20.01.2022)@{uu} 234 | * Added options to select/clear all items 235 | * Added option to save window size/position 236 | * Added experimental hierarchical browser mode 237 | * Added Date column to the archive view 238 | * Added progress bar 239 | * Window now accepts icons dropped on it 240 | * Now correctly sets file protection bits, date and comments 241 | * Fixed some layout issues 242 | 243 | @{u}1.1 (11.01.2022)@{uu} 244 | * First release 245 | @endnode 246 | 247 | @node locale "Translations" 248 | Avalanche supports localisation using AmigaOS catalog files. 249 | The built-in language is English. This is the only official translation. 250 | Catalogs for other languages may be created by using the translation files in "catalogs", and can be distributed separately. 251 | @endnode 252 | 253 | @node contact "Contact" 254 | The best way to report bugs and request features is to submit them to the issue tracker at https://github.com/chris-y/avalanche 255 | 256 | @endnode 257 | -------------------------------------------------------------------------------- /Avalanche.guide.info: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/chris-y/avalanche/d32bc64424e88d857c8db56bfef035dfc7af7316/Avalanche.guide.info -------------------------------------------------------------------------------- /Avalanche.info: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/chris-y/avalanche/d32bc64424e88d857c8db56bfef035dfc7af7316/Avalanche.info -------------------------------------------------------------------------------- /AvalanchePPC.info: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/chris-y/avalanche/d32bc64424e88d857c8db56bfef035dfc7af7316/AvalanchePPC.info -------------------------------------------------------------------------------- /Install: -------------------------------------------------------------------------------- 1 | (procedure p_setdeftool #type 2 | (set #def (cat "def_" #type)) 3 | (tooltype 4 | (prompt "Setting default tool for " #type) 5 | (help @tooltype-help) 6 | (dest (tackon "ENVARC:Sys/" #def)) 7 | (setdefaulttool (tackon @default-dest #Avalanche)) 8 | ) 9 | ) 10 | 11 | ; START 12 | (set #os-vernum (getversion "libs:version.library")) 13 | (set #os-ver (/ #os-vernum 65536)) 14 | 15 | (transcript "Running on OS v" #os-ver) 16 | 17 | (if (< #os-ver 50) 18 | ( 19 | (set #tools-dir "SYS:Tools") 20 | (set #avalanche "Avalanche") 21 | 22 | (set #arc-7zip "") 23 | (set #arc-arj "") 24 | (set #arc-bz2 "") 25 | (set #arc-gzip "") 26 | (set #arc-lha "") 27 | (set #arc-lharc "") 28 | (set #arc-lzx "") 29 | (set #arc-pkzip "") 30 | (set #arc-rar "") 31 | (set #arc-tar "") 32 | (set #arc-zip "") 33 | (set #arc-zoo "") 34 | 35 | (set #xvs-ver 0) 36 | ) 37 | ; else 38 | ( 39 | ; OS4 doesn't have Tools. 40 | 41 | (set #tools-dir (getenv "AppDir/AvalanchePPC")) 42 | 43 | (if (= #tools-dir "") (set #tools-dir "SYS:Utilities")) 44 | (set #avalanche "AvalanchePPC") 45 | 46 | (set #arc-7zip "7zip") 47 | (set #arc-arj "arj") 48 | (set #arc-bz2 "bz2") 49 | (set #arc-gzip "gzip") 50 | (set #arc-lha "lha") 51 | (set #arc-lharc "lharc") 52 | (set #arc-lzx "lzx") 53 | (set #arc-pkzip "pkzip") 54 | (set #arc-rar "rar") 55 | (set #arc-tar "tar") 56 | (set #arc-zip "zip") 57 | (set #arc-zoo "zoo") 58 | 59 | (set #xvs-vernum (getversion "libs:xvs.library")) 60 | (set #xvs-ver (/ #xvs-vernum 65536)) 61 | (transcript "xvs.library v" #xvs-ver) 62 | ) 63 | ) 64 | 65 | (set #xad-ver (getversion "libs:xadmaster.library")) 66 | 67 | (if (= #xad-ver 0) 68 | ( 69 | (message "Please note that this program requires xadmaster.library!\n\n" 70 | "You will need to install it before running Avalanche. " 71 | "It can be downloaded from Aminet util/arc" (all)) 72 | ) 73 | ) 74 | 75 | (welcome) 76 | 77 | (set @default-dest 78 | (askdir 79 | (prompt "Please select where you would like Avalanche to be installed" 80 | " (a drawer will NOT be created)") 81 | (help @askdir-help) 82 | (default #tools-dir) 83 | ) 84 | ) 85 | 86 | (set #doc-dest 87 | (askdir 88 | (prompt "Please select where you would like the Avalanche " 89 | "documentation to be installed (a drawer will NOT be created)") 90 | (help @askdir-help) 91 | (default "LOCALE:Help") 92 | ) 93 | ) 94 | 95 | (set #full-path (tackon @default-dest #Avalanche)) 96 | (set #icon-exists (exists (cat #full-path ".info"))) 97 | 98 | (copyfiles 99 | (prompt "Copying Avalanche") 100 | (help @copyfiles-help) 101 | (source #Avalanche) 102 | (dest @default-dest) 103 | ) 104 | 105 | ; copy xvs.l.main on os4 106 | (if (>= #xvs-ver 33) 107 | ( 108 | (copyfiles 109 | (prompt "Copying xvs.l.main") 110 | (help @copyfiles-help) 111 | (source "libs/xvs.l.main") 112 | (dest "libs:") 113 | ) 114 | ) 115 | ) 116 | 117 | ; Don't overwrite existing icon 118 | (if (= #icon-exists 0) 119 | ( 120 | (copyfiles 121 | (prompt "Copying Avalanche icon") 122 | (help @copyfiles-help) 123 | (source (cat #Avalanche ".info")) 124 | (dest @default-dest) 125 | ) 126 | ) 127 | ) 128 | 129 | (copyfiles 130 | (prompt "Copying Avalanche Guide") 131 | (help @copyfiles-help) 132 | (source "Avalanche.guide") 133 | (dest #doc-dest) 134 | ) 135 | 136 | (set #def-icons 137 | (askoptions 138 | (prompt "Set default tool for the following filetypes:") 139 | (help "AmigaOS 3.2 by default has one default icon for all archives. " 140 | "Selecting \"archive\" here will set Avalanche as the default tool " 141 | "for all archives.") 142 | (choices "archive" 143 | #arc-7zip 144 | #arc-arj 145 | #arc-bz2 146 | #arc-gzip 147 | #arc-lha 148 | #arc-lharc 149 | #arc-lzx 150 | #arc-pkzip 151 | #arc-rar 152 | #arc-tar 153 | #arc-zip 154 | #arc-zoo) 155 | ) 156 | ) 157 | 158 | (if (BITAND #def-icons 1) (p_setdeftool "archive")) 159 | (if (BITAND #def-icons 2) (p_setdeftool #arc-7zip)) 160 | (if (BITAND #def-icons 4) (p_setdeftool #arc-arj)) 161 | (if (BITAND #def-icons 8) (p_setdeftool #arc-bz2)) 162 | (if (BITAND #def-icons 16) (p_setdeftool #arc-gzip)) 163 | (if (BITAND #def-icons 32) (p_setdeftool #arc-lha)) 164 | (if (BITAND #def-icons 64) (p_setdeftool #arc-lharc)) 165 | (if (BITAND #def-icons 128) (p_setdeftool #arc-lzx)) 166 | (if (BITAND #def-icons 256) (p_setdeftool #arc-pkzip)) 167 | (if (BITAND #def-icons 512) (p_setdeftool #arc-rar)) 168 | (if (BITAND #def-icons 1024) (p_setdeftool #arc-tar)) 169 | (if (BITAND #def-icons 2048) (p_setdeftool #arc-zip)) 170 | (if (BITAND #def-icons 4096) (p_setdeftool #arc-zoo)) 171 | -------------------------------------------------------------------------------- /Install.info: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/chris-y/avalanche/d32bc64424e88d857c8db56bfef035dfc7af7316/Install.info -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | GNU GENERAL PUBLIC LICENSE 2 | Version 2, June 1991 3 | 4 | Copyright (C) 1989, 1991 Free Software Foundation, Inc., 5 | 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 6 | Everyone is permitted to copy and distribute verbatim copies 7 | of this license document, but changing it is not allowed. 8 | 9 | Preamble 10 | 11 | The licenses for most software are designed to take away your 12 | freedom to share and change it. By contrast, the GNU General Public 13 | License is intended to guarantee your freedom to share and change free 14 | software--to make sure the software is free for all its users. This 15 | General Public License applies to most of the Free Software 16 | Foundation's software and to any other program whose authors commit to 17 | using it. (Some other Free Software Foundation software is covered by 18 | the GNU Lesser General Public License instead.) You can apply it to 19 | your programs, too. 20 | 21 | When we speak of free software, we are referring to freedom, not 22 | price. Our General Public Licenses are designed to make sure that you 23 | have the freedom to distribute copies of free software (and charge for 24 | this service if you wish), that you receive source code or can get it 25 | if you want it, that you can change the software or use pieces of it 26 | in new free programs; and that you know you can do these things. 27 | 28 | To protect your rights, we need to make restrictions that forbid 29 | anyone to deny you these rights or to ask you to surrender the rights. 30 | These restrictions translate to certain responsibilities for you if you 31 | distribute copies of the software, or if you modify it. 32 | 33 | For example, if you distribute copies of such a program, whether 34 | gratis or for a fee, you must give the recipients all the rights that 35 | you have. You must make sure that they, too, receive or can get the 36 | source code. And you must show them these terms so they know their 37 | rights. 38 | 39 | We protect your rights with two steps: (1) copyright the software, and 40 | (2) offer you this license which gives you legal permission to copy, 41 | distribute and/or modify the software. 42 | 43 | Also, for each author's protection and ours, we want to make certain 44 | that everyone understands that there is no warranty for this free 45 | software. If the software is modified by someone else and passed on, we 46 | want its recipients to know that what they have is not the original, so 47 | that any problems introduced by others will not reflect on the original 48 | authors' reputations. 49 | 50 | Finally, any free program is threatened constantly by software 51 | patents. We wish to avoid the danger that redistributors of a free 52 | program will individually obtain patent licenses, in effect making the 53 | program proprietary. To prevent this, we have made it clear that any 54 | patent must be licensed for everyone's free use or not licensed at all. 55 | 56 | The precise terms and conditions for copying, distribution and 57 | modification follow. 58 | 59 | GNU GENERAL PUBLIC LICENSE 60 | TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION 61 | 62 | 0. This License applies to any program or other work which contains 63 | a notice placed by the copyright holder saying it may be distributed 64 | under the terms of this General Public License. The "Program", below, 65 | refers to any such program or work, and a "work based on the Program" 66 | means either the Program or any derivative work under copyright law: 67 | that is to say, a work containing the Program or a portion of it, 68 | either verbatim or with modifications and/or translated into another 69 | language. (Hereinafter, translation is included without limitation in 70 | the term "modification".) Each licensee is addressed as "you". 71 | 72 | Activities other than copying, distribution and modification are not 73 | covered by this License; they are outside its scope. The act of 74 | running the Program is not restricted, and the output from the Program 75 | is covered only if its contents constitute a work based on the 76 | Program (independent of having been made by running the Program). 77 | Whether that is true depends on what the Program does. 78 | 79 | 1. You may copy and distribute verbatim copies of the Program's 80 | source code as you receive it, in any medium, provided that you 81 | conspicuously and appropriately publish on each copy an appropriate 82 | copyright notice and disclaimer of warranty; keep intact all the 83 | notices that refer to this License and to the absence of any warranty; 84 | and give any other recipients of the Program a copy of this License 85 | along with the Program. 86 | 87 | You may charge a fee for the physical act of transferring a copy, and 88 | you may at your option offer warranty protection in exchange for a fee. 89 | 90 | 2. You may modify your copy or copies of the Program or any portion 91 | of it, thus forming a work based on the Program, and copy and 92 | distribute such modifications or work under the terms of Section 1 93 | above, provided that you also meet all of these conditions: 94 | 95 | a) You must cause the modified files to carry prominent notices 96 | stating that you changed the files and the date of any change. 97 | 98 | b) You must cause any work that you distribute or publish, that in 99 | whole or in part contains or is derived from the Program or any 100 | part thereof, to be licensed as a whole at no charge to all third 101 | parties under the terms of this License. 102 | 103 | c) If the modified program normally reads commands interactively 104 | when run, you must cause it, when started running for such 105 | interactive use in the most ordinary way, to print or display an 106 | announcement including an appropriate copyright notice and a 107 | notice that there is no warranty (or else, saying that you provide 108 | a warranty) and that users may redistribute the program under 109 | these conditions, and telling the user how to view a copy of this 110 | License. (Exception: if the Program itself is interactive but 111 | does not normally print such an announcement, your work based on 112 | the Program is not required to print an announcement.) 113 | 114 | These requirements apply to the modified work as a whole. If 115 | identifiable sections of that work are not derived from the Program, 116 | and can be reasonably considered independent and separate works in 117 | themselves, then this License, and its terms, do not apply to those 118 | sections when you distribute them as separate works. But when you 119 | distribute the same sections as part of a whole which is a work based 120 | on the Program, the distribution of the whole must be on the terms of 121 | this License, whose permissions for other licensees extend to the 122 | entire whole, and thus to each and every part regardless of who wrote it. 123 | 124 | Thus, it is not the intent of this section to claim rights or contest 125 | your rights to work written entirely by you; rather, the intent is to 126 | exercise the right to control the distribution of derivative or 127 | collective works based on the Program. 128 | 129 | In addition, mere aggregation of another work not based on the Program 130 | with the Program (or with a work based on the Program) on a volume of 131 | a storage or distribution medium does not bring the other work under 132 | the scope of this License. 133 | 134 | 3. You may copy and distribute the Program (or a work based on it, 135 | under Section 2) in object code or executable form under the terms of 136 | Sections 1 and 2 above provided that you also do one of the following: 137 | 138 | a) Accompany it with the complete corresponding machine-readable 139 | source code, which must be distributed under the terms of Sections 140 | 1 and 2 above on a medium customarily used for software interchange; or, 141 | 142 | b) Accompany it with a written offer, valid for at least three 143 | years, to give any third party, for a charge no more than your 144 | cost of physically performing source distribution, a complete 145 | machine-readable copy of the corresponding source code, to be 146 | distributed under the terms of Sections 1 and 2 above on a medium 147 | customarily used for software interchange; or, 148 | 149 | c) Accompany it with the information you received as to the offer 150 | to distribute corresponding source code. (This alternative is 151 | allowed only for noncommercial distribution and only if you 152 | received the program in object code or executable form with such 153 | an offer, in accord with Subsection b above.) 154 | 155 | The source code for a work means the preferred form of the work for 156 | making modifications to it. For an executable work, complete source 157 | code means all the source code for all modules it contains, plus any 158 | associated interface definition files, plus the scripts used to 159 | control compilation and installation of the executable. However, as a 160 | special exception, the source code distributed need not include 161 | anything that is normally distributed (in either source or binary 162 | form) with the major components (compiler, kernel, and so on) of the 163 | operating system on which the executable runs, unless that component 164 | itself accompanies the executable. 165 | 166 | If distribution of executable or object code is made by offering 167 | access to copy from a designated place, then offering equivalent 168 | access to copy the source code from the same place counts as 169 | distribution of the source code, even though third parties are not 170 | compelled to copy the source along with the object code. 171 | 172 | 4. You may not copy, modify, sublicense, or distribute the Program 173 | except as expressly provided under this License. Any attempt 174 | otherwise to copy, modify, sublicense or distribute the Program is 175 | void, and will automatically terminate your rights under this License. 176 | However, parties who have received copies, or rights, from you under 177 | this License will not have their licenses terminated so long as such 178 | parties remain in full compliance. 179 | 180 | 5. You are not required to accept this License, since you have not 181 | signed it. However, nothing else grants you permission to modify or 182 | distribute the Program or its derivative works. These actions are 183 | prohibited by law if you do not accept this License. Therefore, by 184 | modifying or distributing the Program (or any work based on the 185 | Program), you indicate your acceptance of this License to do so, and 186 | all its terms and conditions for copying, distributing or modifying 187 | the Program or works based on it. 188 | 189 | 6. Each time you redistribute the Program (or any work based on the 190 | Program), the recipient automatically receives a license from the 191 | original licensor to copy, distribute or modify the Program subject to 192 | these terms and conditions. You may not impose any further 193 | restrictions on the recipients' exercise of the rights granted herein. 194 | You are not responsible for enforcing compliance by third parties to 195 | this License. 196 | 197 | 7. If, as a consequence of a court judgment or allegation of patent 198 | infringement or for any other reason (not limited to patent issues), 199 | conditions are imposed on you (whether by court order, agreement or 200 | otherwise) that contradict the conditions of this License, they do not 201 | excuse you from the conditions of this License. If you cannot 202 | distribute so as to satisfy simultaneously your obligations under this 203 | License and any other pertinent obligations, then as a consequence you 204 | may not distribute the Program at all. For example, if a patent 205 | license would not permit royalty-free redistribution of the Program by 206 | all those who receive copies directly or indirectly through you, then 207 | the only way you could satisfy both it and this License would be to 208 | refrain entirely from distribution of the Program. 209 | 210 | If any portion of this section is held invalid or unenforceable under 211 | any particular circumstance, the balance of the section is intended to 212 | apply and the section as a whole is intended to apply in other 213 | circumstances. 214 | 215 | It is not the purpose of this section to induce you to infringe any 216 | patents or other property right claims or to contest validity of any 217 | such claims; this section has the sole purpose of protecting the 218 | integrity of the free software distribution system, which is 219 | implemented by public license practices. Many people have made 220 | generous contributions to the wide range of software distributed 221 | through that system in reliance on consistent application of that 222 | system; it is up to the author/donor to decide if he or she is willing 223 | to distribute software through any other system and a licensee cannot 224 | impose that choice. 225 | 226 | This section is intended to make thoroughly clear what is believed to 227 | be a consequence of the rest of this License. 228 | 229 | 8. If the distribution and/or use of the Program is restricted in 230 | certain countries either by patents or by copyrighted interfaces, the 231 | original copyright holder who places the Program under this License 232 | may add an explicit geographical distribution limitation excluding 233 | those countries, so that distribution is permitted only in or among 234 | countries not thus excluded. In such case, this License incorporates 235 | the limitation as if written in the body of this License. 236 | 237 | 9. The Free Software Foundation may publish revised and/or new versions 238 | of the General Public License from time to time. Such new versions will 239 | be similar in spirit to the present version, but may differ in detail to 240 | address new problems or concerns. 241 | 242 | Each version is given a distinguishing version number. If the Program 243 | specifies a version number of this License which applies to it and "any 244 | later version", you have the option of following the terms and conditions 245 | either of that version or of any later version published by the Free 246 | Software Foundation. If the Program does not specify a version number of 247 | this License, you may choose any version ever published by the Free Software 248 | Foundation. 249 | 250 | 10. If you wish to incorporate parts of the Program into other free 251 | programs whose distribution conditions are different, write to the author 252 | to ask for permission. For software which is copyrighted by the Free 253 | Software Foundation, write to the Free Software Foundation; we sometimes 254 | make exceptions for this. Our decision will be guided by the two goals 255 | of preserving the free status of all derivatives of our free software and 256 | of promoting the sharing and reuse of software generally. 257 | 258 | NO WARRANTY 259 | 260 | 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY 261 | FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN 262 | OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES 263 | PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED 264 | OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 265 | MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS 266 | TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE 267 | PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING, 268 | REPAIR OR CORRECTION. 269 | 270 | 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING 271 | WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR 272 | REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, 273 | INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING 274 | OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED 275 | TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY 276 | YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER 277 | PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE 278 | POSSIBILITY OF SUCH DAMAGES. 279 | 280 | END OF TERMS AND CONDITIONS 281 | 282 | How to Apply These Terms to Your New Programs 283 | 284 | If you develop a new program, and you want it to be of the greatest 285 | possible use to the public, the best way to achieve this is to make it 286 | free software which everyone can redistribute and change under these terms. 287 | 288 | To do so, attach the following notices to the program. It is safest 289 | to attach them to the start of each source file to most effectively 290 | convey the exclusion of warranty; and each file should have at least 291 | the "copyright" line and a pointer to where the full notice is found. 292 | 293 | 294 | Copyright (C) 295 | 296 | This program is free software; you can redistribute it and/or modify 297 | it under the terms of the GNU General Public License as published by 298 | the Free Software Foundation; either version 2 of the License, or 299 | (at your option) any later version. 300 | 301 | This program is distributed in the hope that it will be useful, 302 | but WITHOUT ANY WARRANTY; without even the implied warranty of 303 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 304 | GNU General Public License for more details. 305 | 306 | You should have received a copy of the GNU General Public License along 307 | with this program; if not, write to the Free Software Foundation, Inc., 308 | 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 309 | 310 | Also add information on how to contact you by electronic and paper mail. 311 | 312 | If the program is interactive, make it output a short notice like this 313 | when it starts in an interactive mode: 314 | 315 | Gnomovision version 69, Copyright (C) year name of author 316 | Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'. 317 | This is free software, and you are welcome to redistribute it 318 | under certain conditions; type `show c' for details. 319 | 320 | The hypothetical commands `show w' and `show c' should show the appropriate 321 | parts of the General Public License. Of course, the commands you use may 322 | be called something other than `show w' and `show c'; they could even be 323 | mouse-clicks or menu items--whatever suits your program. 324 | 325 | You should also get your employer (if you work as a programmer) or your 326 | school, if any, to sign a "copyright disclaimer" for the program, if 327 | necessary. Here is a sample; alter the names: 328 | 329 | Yoyodyne, Inc., hereby disclaims all copyright interest in the program 330 | `Gnomovision' (which makes passes at compilers) written by James Hacker. 331 | 332 | , 1 April 1989 333 | Ty Coon, President of Vice 334 | 335 | This General Public License does not permit incorporating your program into 336 | proprietary programs. If your program is a subroutine library, you may 337 | consider it more useful to permit linking proprietary applications with the 338 | library. If this is what you want to do, use the GNU Lesser General 339 | Public License instead of this License. 340 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Avalanche 2 | Simple ReAction GUI for XAD 3 | -------------------------------------------------------------------------------- /avalanche.readme: -------------------------------------------------------------------------------- 1 | Short: ReAction unarchive GUI for xfd/xadmaster 2 | Uploader: chris@unsatisfactorysoftware.co.uk (Chris Young) 3 | Author: chris@unsatisfactorysoftware.co.uk (Chris Young) 4 | Type: util/arc 5 | Version: 2.4 6 | Architecture: m68k-amigaos >= 3.2.1; ppc-amigaos >= 4.1.0 7 | Requires: util/arc/xadmaster000.lha 8 | 9 | This is a simple GUI for xadmaster.library using the ReAction 10 | gadget set, written as all the others on Aminet appear to 11 | require MUI. It also supports decrunching with xfdmaster.library, 12 | scanning for viruses with xvs.library, and simple editing of LhA/Zip 13 | archives (Zip needs zip.library - OS4 only). 14 | 15 | This is designed for AmigaOS 3.2.1 (and tested on that and OS4). It 16 | probably won't work on older versions as it needs a new window.class :) 17 | All use is at your own risk. 18 | 19 | GPL, source code available on website. 20 | 21 | Changes in this version: 22 | * Support Deark (needs enabling by tooltype) 23 | This is a "beta" feature, it may be unstable and due to a bug in 24 | Deark, it is not possible to extract to the root of any device. 25 | * Add option to select modules (MODULES tooltype) 26 | * Fix password caching 27 | * Also use T: as temp by default from CLI 28 | 29 | -- To enable Deark, add MODULES=XAD|XFD|DEARK to tooltypes. 30 | 31 | 32 | For full history see documentation inside the archive. 33 | -------------------------------------------------------------------------------- /avalanche.readme.info: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/chris-y/avalanche/d32bc64424e88d857c8db56bfef035dfc7af7316/avalanche.readme.info -------------------------------------------------------------------------------- /catalogs/avalanche.cd: -------------------------------------------------------------------------------- 1 | ## header LOCALE_STRINGS_H 2 | ## array cat_strings 3 | ## function locale_get_string 4 | ; 5 | MSG_EXTRACT (//) 6 | E_xtract 7 | ; 8 | MSG_SAVE (//) 9 | Save 10 | ; 11 | MSG_USE (//) 12 | Use 13 | ; 14 | MSG_CANCEL (//) 15 | Cancel 16 | ; 17 | MSG_PREFERENCES (//) 18 | Preferences... 19 | ; 20 | MSG_PROJECT (//) 21 | Project 22 | ; 23 | MSG_OPEN (//) 24 | Open... 25 | ; 26 | MSG_ARCHIVEINFO (//) 27 | Archive info... 28 | ; 29 | MSG_ABOUT (//) 30 | About... 31 | ; 32 | MSG_QUIT (//) 33 | Quit... 34 | ; 35 | MSG_EDIT (//) 36 | Edit 37 | ; 38 | MSG_SELECTALL (//) 39 | Select all 40 | ; 41 | MSG_CLEARSELECTION (//) 42 | Clear selection 43 | ; 44 | MSG_INVERTSELECTION (//) 45 | Invert selection 46 | ; 47 | MSG_SETTINGS (//) 48 | Settings 49 | ; 50 | MSG_SCANFORVIRUSES (//) 51 | Scan for viruses 52 | ; 53 | MSG_HIERARCHICALBROWSEREXPERIMENTAL (//) 54 | Hierarchical browser (experimental) 55 | ; 56 | MSG_SAVEWINDOWPOSITION (//) 57 | Save window position 58 | ; 59 | MSG_CONFIRMQUIT (//) 60 | Confirm quit 61 | ; 62 | MSG_SAVESETTINGS (//) 63 | Save settings 64 | ; 65 | MSG_STOP (//) 66 | _Stop 67 | ; 68 | MSG_NAME (//) 69 | Name 70 | ; 71 | MSG_SIZE (//) 72 | Size 73 | ; 74 | MSG_DATE (//) 75 | Date 76 | ; 77 | MSG_SELECTARCHIVE (//) 78 | Select Archive 79 | ; 80 | MSG_ARCHIVE (//) 81 | _Archive 82 | ; 83 | MSG_SELECTDESTINATION (//) 84 | Select Destination 85 | ; 86 | MSG_DESTINATION (//) 87 | _Destination 88 | ; 89 | MSG_ALREADYEXISTSOVERWRITE (//) 90 | %s already exists, overwrite? 91 | ; 92 | MSG_FILEARCHIVE (//) 93 | file archive 94 | ; 95 | MSG_DISKARCHIVE (//) 96 | disk archive 97 | ; 98 | MSG_DISKIMAGE (//) 99 | disk image 100 | ; 101 | MSG_UNKNOWN (//) 102 | unknown 103 | ; 104 | MSG_OK (//) 105 | _OK 106 | ; 107 | MSG_CRUNCHED (//) 108 | %s crunched 109 | ; 110 | MSG_ERRORDECRUNCHING (//) 111 | Error decrunching 112 | ; 113 | MSG_VIRUSSCANNINGWILLBEDISABLED (//) 114 | Virus scanning will be disabled.\n 115 | ; 116 | MSG_XVSLIBRARYFAILEDSELFTEST (//) 117 | xvs.library failed self-test, 118 | ; 119 | MSG_OUTOFMEMORYSCANNINGFILE (//) 120 | Out of memory scanning file:\n%s 121 | ; 122 | MSG_FILEHASBEENDELETED (//) 123 | File has been deleted. 124 | ; 125 | MSG_FILECOULDNOTBEDELETED (//) 126 | File could not be deleted. 127 | ; 128 | MSG_VIRUSFOUNDETECTIONNAME (//) 129 | Virus found in %s\nDetection name: %s\n\n 130 | ; 131 | MSG_GPL (//) 132 | This program is free software; you can redistribute it and/or modify\nit under the terms of the GNU General Public License as published by\nthe Free Software Foundation; either version 2 of the \ 133 | License, or\n(at your option) any later version.\n\nThis program is distributed in the hope that it will be useful,\nbut WITHOUT ANY WARRANTY; without even the implied warranty of\nMERCHANTABILITY or \ 134 | FITNESS FOR A PARTICULAR PURPOSE. See the\nGNU General Public License for more details. 135 | ; 136 | MSG_UNABLETOOPENREQUESTERTOSHOWERRORS (//) 137 | Unable to open requester to show error;\n%s [%s]\n 138 | ; 139 | MSG_UNABLETOOPENLIBRARY (//) 140 | Unable to open %s v%d\n 141 | ; 142 | MSG_AREYOUSUREYOUWANTTOEXIT (//) 143 | Are you sure you want to exit? 144 | ; 145 | MSG_YESNO (//) 146 | _Yes|_No 147 | ; 148 | MSG_YESYESTOALLNONOTOALLABORT (//) 149 | _Yes|Yes to _all|_No|N_o to all|Abort 150 | ; 151 | MSG_ARCHIVEISENCRYPTEDPLEASEENTERPASSWORD (//) 152 | Archive is encrypted, please enter password. 153 | ; 154 | MSG_OKCANCEL (//) 155 | _OK|_Cancel 156 | ; 157 | MSG_UNABLETOOPENREQUESTERTOASKPASSWORD (//) 158 | Unable to open requester to ask password\n 159 | MSG_INTERFACE (//) 160 | (interface) 161 | ; 162 | MSG_IGNOREFILESYSTEMS (//) 163 | Ignore filesystems 164 | ; 165 | MSG_CXDESCRIPTION (//) 166 | Unarchive GUI for XAD/XFD 167 | ; 168 | MSG_APPMENU_EXTRACTHERE (//) 169 | Extract here 170 | ; 171 | MSG_SNAPSHOT (//) 172 | Snapshot window 173 | ; 174 | MSG_UNABLETOOPENFILE (//) 175 | Unable to open file 176 | ; 177 | MSG_OUTOFMEMORY (//) 178 | Not enough memory 179 | ; 180 | MSG_LASTWINDOWCLOSED (//) 181 | Last window closed. 182 | ; 183 | MSG_QUITHIDECANCEL (//) 184 | Quit|Hide|Cancel 185 | ; 186 | MSG_NEWWINDOW (//) 187 | New window... 188 | ; 189 | MSG_QUITCFG_ASK (//) 190 | Ask 191 | ; 192 | MSG_QUITCFG_QUIT (//) 193 | Quit 194 | ; 195 | MSG_QUITCFG_HIDE (//) 196 | Hide 197 | ; 198 | MSG_LASTWINDOWACTION (//) 199 | When last window closed: 200 | ; 201 | MSG_ADDFILES (//) 202 | Add files... 203 | ; 204 | MSG_DELFILES (//) 205 | Delete selected items... 206 | ; 207 | MSG_UNABLETOOPENZIP (//) 208 | Unable to open Zip for writing 209 | ; 210 | MSG_LHAERROR (//) 211 | Error processing file: %s 212 | ; 213 | MSG_SKIPRETRYABORT (//) 214 | Skip|Retry|Abort 215 | ; 216 | MSG_ARCHIVEMUSTHAVEENTRIES (//) 217 | Archive must contain at least one file. 218 | ; 219 | MSG_CONFIRMDELETE (//) 220 | Are you sure you want to delete the selected entries? 221 | ; 222 | MSG_VIEWMODEBROWSER (//) 223 | Browser 224 | ; 225 | MSG_VIEWMODELIST (//) 226 | List 227 | ; 228 | MSG_VIEWMODE (//) 229 | View mode 230 | ; 231 | MSG_ERR_TREE_ALLOC (//) 232 | Tree entries exceed allocated memory 233 | ; 234 | MSG_NEWARCHIVE (//) 235 | New archive... 236 | ; 237 | MSG_TYPE (//) 238 | _Type 239 | ; 240 | MSG_CREATE (//) 241 | _Create 242 | ; 243 | MSG_DIR (//) 244 | (dir) 245 | ; 246 | MSG_PARENT (//) 247 | (parent) 248 | ; 249 | MSG_PACKEDSIZE (//) 250 | Packed Size 251 | ; 252 | MSG_SNAPSHOT_WARNING (//) 253 | This will not be persistent until prefs are saved! 254 | ; 255 | MSG_ERR_NOTCPIP (//) 256 | Please start your TCP/IP stack 257 | ; 258 | MSG_ERR_AMISSL (//) 259 | Unable to open AmiSSL v5 260 | ; 261 | MSG_ERR_UNKNOWN (//) 262 | Unknown error 263 | ; 264 | MSG_NEWVERSION (//) 265 | New version (%s) available 266 | ; 267 | MSG_NONEWVERSION (//) 268 | Current version is up-to-date 269 | ; 270 | MSG_CHECKVERSION (//) 271 | Check for update... 272 | ; 273 | -------------------------------------------------------------------------------- /catalogs/avalanche.cs: -------------------------------------------------------------------------------- 1 | ## Version $VER: avalanche.catalog 1.0 (15.05.2022) 2 | ## Languages english 3 | ## Codeset english 0 4 | ## SimpleCatConfig CharsPerLine 200 5 | ## Header LOCALE_STRINGS_H 6 | ## Array cat_strings 7 | ## Function locale_get_string 8 | ; 9 | MSG_EXTRACT 10 | E_xtract 11 | ; 12 | MSG_SAVE 13 | Save 14 | ; 15 | MSG_USE 16 | Use 17 | ; 18 | MSG_CANCEL 19 | Cancel 20 | ; 21 | MSG_PREFERENCES 22 | Preferences... 23 | ; 24 | MSG_PROJECT 25 | Project 26 | ; 27 | MSG_OPEN 28 | Open... 29 | ; 30 | MSG_ARCHIVEINFO 31 | Archive info... 32 | ; 33 | MSG_ABOUT 34 | About... 35 | ; 36 | MSG_QUIT 37 | Quit... 38 | ; 39 | MSG_EDIT 40 | Edit 41 | ; 42 | MSG_SELECTALL 43 | Select all 44 | ; 45 | MSG_CLEARSELECTION 46 | Clear selection 47 | ; 48 | MSG_INVERTSELECTION 49 | Invert selection 50 | ; 51 | MSG_SETTINGS 52 | Settings 53 | ; 54 | MSG_SCANFORVIRUSES 55 | Scan for viruses 56 | ; 57 | MSG_HIERARCHICALBROWSEREXPERIMENTAL 58 | Hierarchical browser (experimental) 59 | ; 60 | MSG_SAVEWINDOWPOSITION 61 | Save window position 62 | ; 63 | MSG_CONFIRMQUIT 64 | Confirm quit 65 | ; 66 | MSG_SAVESETTINGS 67 | Save settings 68 | ; 69 | MSG_STOP 70 | _Stop 71 | ; 72 | MSG_NAME 73 | Name 74 | ; 75 | MSG_SIZE 76 | Size 77 | ; 78 | MSG_DATE 79 | Date 80 | ; 81 | MSG_SELECTARCHIVE 82 | Select Archive 83 | ; 84 | MSG_ARCHIVE 85 | _Archive 86 | ; 87 | MSG_SELECTDESTINATION 88 | Select Destination 89 | ; 90 | MSG_DESTINATION 91 | _Destination 92 | ; 93 | MSG_ALREADYEXISTSOVERWRITE 94 | %s already exists, overwrite? 95 | ; 96 | MSG_FILEARCHIVE 97 | file archive 98 | ; 99 | MSG_DISKARCHIVE 100 | disk archive 101 | ; 102 | MSG_DISKIMAGE 103 | disk image 104 | ; 105 | MSG_UNKNOWN 106 | unknown 107 | ; 108 | MSG_OK 109 | _OK 110 | ; 111 | MSG_CRUNCHED 112 | %s crunched 113 | ; 114 | MSG_ERRORDECRUNCHING 115 | Error decrunching 116 | ; 117 | MSG_VIRUSSCANNINGWILLBEDISABLED 118 | Virus scanning will be disabled.\n 119 | ; 120 | MSG_XVSLIBRARYFAILEDSELFTEST 121 | xvs.library failed self-test, 122 | ; 123 | MSG_OUTOFMEMORYSCANNINGFILE 124 | Out of memory scanning file:\n%s 125 | ; 126 | MSG_FILEHASBEENDELETED 127 | File has been deleted. 128 | ; 129 | MSG_FILECOULDNOTBEDELETED 130 | File could not be deleted. 131 | ; 132 | MSG_VIRUSFOUNDETECTIONNAME 133 | Virus found in %s\nDetection name: %s\n\n 134 | ; 135 | MSG_GPL 136 | This program is free software; you can redistribute it and/or modify\nit under the terms of the GNU General Public License as published by\nthe Free Software Foundation; either version 2 of the \ 137 | License, or\n(at your option) any later version.\n\nThis program is distributed in the hope that it will be useful,\nbut WITHOUT ANY WARRANTY; without even the implied warranty of\nMERCHANTABILITY or \ 138 | FITNESS FOR A PARTICULAR PURPOSE. See the\nGNU General Public License for more details. 139 | ; 140 | MSG_UNABLETOOPENREQUESTERTOSHOWERRORS 141 | Unable to open requester to show error;\n%s [%s]\n 142 | ; 143 | MSG_UNABLETOOPENLIBRARY 144 | Unable to open %s v%d\n 145 | ; 146 | MSG_AREYOUSUREYOUWANTTOEXIT 147 | Are you sure you want to exit? 148 | ; 149 | MSG_YESNO 150 | _Yes|_No 151 | ; 152 | MSG_YESYESTOALLNONOTOALLABORT 153 | _Yes|Yes to _all|_No|N_o to all|Abort 154 | ; 155 | MSG_ARCHIVEISENCRYPTEDPLEASEENTERPASSWORD 156 | Archive is encrypted, please enter password. 157 | ; 158 | MSG_OKCANCEL 159 | _OK|_Cancel 160 | ; 161 | MSG_UNABLETOOPENREQUESTERTOASKPASSWORD 162 | Unable to open requester to ask password\n 163 | MSG_INTERFACE 164 | (interface) 165 | ; 166 | MSG_IGNOREFILESYSTEMS 167 | Ignore filesystems 168 | ; 169 | MSG_CXDESCRIPTION 170 | Unarchive GUI for XAD/XFD 171 | ; 172 | MSG_APPMENU_EXTRACTHERE 173 | Extract here 174 | ; 175 | MSG_SNAPSHOT 176 | Snapshot window 177 | ; 178 | MSG_UNABLETOOPENFILE 179 | Unable to open file 180 | ; 181 | MSG_OUTOFMEMORY 182 | Not enough memory 183 | ; 184 | MSG_LASTWINDOWCLOSED 185 | Last window closed. 186 | ; 187 | MSG_QUITHIDECANCEL 188 | Quit|Hide|Cancel 189 | ; 190 | MSG_NEWWINDOW 191 | New window... 192 | ; 193 | MSG_QUITCFG_ASK 194 | Ask 195 | ; 196 | MSG_QUITCFG_QUIT 197 | Quit 198 | ; 199 | MSG_QUITCFG_HIDE 200 | Hide 201 | ; 202 | MSG_LASTWINDOWACTION 203 | When last window closed: 204 | ; 205 | MSG_ADDFILES 206 | Add files... 207 | ; 208 | MSG_DELFILES 209 | Delete selected items... 210 | ; 211 | MSG_UNABLETOOPENZIP 212 | Unable to open Zip for writing 213 | ; 214 | MSG_LHAERROR 215 | Error processing file: %s 216 | ; 217 | MSG_SKIPRETRYABORT 218 | Skip|Retry|Abort 219 | ; 220 | MSG_ARCHIVEMUSTHAVEENTRIES 221 | Archive must contain at least one file. 222 | ; 223 | MSG_CONFIRMDELETE 224 | Are you sure you want to delete the selected entries? 225 | ; 226 | MSG_VIEWMODEBROWSER 227 | Browser 228 | ; 229 | MSG_VIEWMODELIST 230 | List 231 | ; 232 | MSG_VIEWMODE 233 | View mode 234 | ; 235 | MSG_ERR_TREE_ALLOC 236 | Tree entries exceed allocated memory 237 | ; 238 | MSG_NEWARCHIVE 239 | New archive... 240 | ; 241 | MSG_TYPE 242 | _Type 243 | ; 244 | MSG_CREATE 245 | _Create 246 | ; 247 | MSG_DIR 248 | (dir) 249 | ; 250 | MSG_PARENT 251 | (parent) 252 | ; 253 | MSG_PACKEDSIZE 254 | Packed Size 255 | ; 256 | MSG_SNAPSHOT_WARNING 257 | This will not be persistent until prefs are saved! 258 | ; 259 | MSG_ERR_NOTCPIP 260 | Please start your TCP/IP stack 261 | ; 262 | MSG_ERR_AMISSL 263 | Unable to open AmiSSL v5 264 | ; 265 | MSG_ERR_UNKNOWN 266 | Unknown error 267 | ; 268 | MSG_NEWVERSION 269 | New version (%s) available 270 | ; 271 | MSG_NONEWVERSION 272 | Current version is up-to-date 273 | ; 274 | MSG_CHECKVERSION 275 | Check for update... 276 | ; 277 | -------------------------------------------------------------------------------- /catalogs/avalanche.ct: -------------------------------------------------------------------------------- 1 | ## version $VER: avalanche.catalog 1.0 (15.05.2022) 2 | ## codeset 0 3 | ## language english 4 | ; 5 | MSG_EXTRACT 6 | E_xtract 7 | ; E_xtract 8 | ; 9 | MSG_SAVE 10 | Save 11 | ; Save 12 | ; 13 | MSG_USE 14 | Use 15 | ; Use 16 | ; 17 | MSG_CANCEL 18 | Cancel 19 | ; Cancel 20 | ; 21 | MSG_PREFERENCES 22 | Preferences... 23 | ; Preferences... 24 | ; 25 | MSG_PROJECT 26 | Project 27 | ; Project 28 | ; 29 | MSG_OPEN 30 | Open... 31 | ; Open... 32 | ; 33 | MSG_ARCHIVEINFO 34 | Archive info... 35 | ; Archive info... 36 | ; 37 | MSG_ABOUT 38 | About... 39 | ; About... 40 | ; 41 | MSG_QUIT 42 | Quit... 43 | ; Quit... 44 | ; 45 | MSG_EDIT 46 | Edit 47 | ; Edit 48 | ; 49 | MSG_SELECTALL 50 | Select all 51 | ; Select all 52 | ; 53 | MSG_CLEARSELECTION 54 | Clear selection 55 | ; Clear selection 56 | ; 57 | MSG_INVERTSELECTION 58 | Invert selection 59 | ; Invert selection 60 | ; 61 | MSG_SETTINGS 62 | Settings 63 | ; Settings 64 | ; 65 | MSG_SCANFORVIRUSES 66 | Scan for viruses 67 | ; Scan for viruses 68 | ; 69 | MSG_HIERARCHICALBROWSEREXPERIMENTAL 70 | Hierarchical browser (experimental) 71 | ; Hierarchical browser (experimental) 72 | ; 73 | MSG_SAVEWINDOWPOSITION 74 | Save window position 75 | ; Save window position 76 | ; 77 | MSG_CONFIRMQUIT 78 | Confirm quit 79 | ; Confirm quit 80 | ; 81 | MSG_SAVESETTINGS 82 | Save settings 83 | ; Save settings 84 | ; 85 | MSG_STOP 86 | _Stop 87 | ; _Stop 88 | ; 89 | MSG_NAME 90 | Name 91 | ; Name 92 | ; 93 | MSG_SIZE 94 | Size 95 | ; Size 96 | ; 97 | MSG_DATE 98 | Date 99 | ; Date 100 | ; 101 | MSG_SELECTARCHIVE 102 | Select Archive 103 | ; Select Archive 104 | ; 105 | MSG_ARCHIVE 106 | _Archive 107 | ; _Archive 108 | ; 109 | MSG_SELECTDESTINATION 110 | Select Destination 111 | ; Select Destination 112 | ; 113 | MSG_DESTINATION 114 | _Destination 115 | ; _Destination 116 | ; 117 | MSG_ALREADYEXISTSOVERWRITE 118 | %s already exists, overwrite? 119 | ; %s already exists, overwrite? 120 | ; 121 | MSG_FILEARCHIVE 122 | file archive 123 | ; file archive 124 | ; 125 | MSG_DISKARCHIVE 126 | disk archive 127 | ; disk archive 128 | ; 129 | MSG_DISKIMAGE 130 | disk image 131 | ; disk image 132 | ; 133 | MSG_UNKNOWN 134 | unknown 135 | ; unknown 136 | ; 137 | MSG_OK 138 | _OK 139 | ; _OK 140 | ; 141 | MSG_CRUNCHED 142 | %s crunched 143 | ; %s crunched 144 | ; 145 | MSG_ERRORDECRUNCHING 146 | Error decrunching 147 | ; Error decrunching 148 | ; 149 | MSG_VIRUSSCANNINGWILLBEDISABLED 150 | Virus scanning will be disabled.\n 151 | ; Virus scanning will be disabled.\n 152 | ; 153 | MSG_XVSLIBRARYFAILEDSELFTEST 154 | xvs.library failed self-test, 155 | ; xvs.library failed self-test, 156 | ; 157 | MSG_OUTOFMEMORYSCANNINGFILE 158 | Out of memory scanning file:\n%s 159 | ; Out of memory scanning file:\n%s 160 | ; 161 | MSG_FILEHASBEENDELETED 162 | File has been deleted. 163 | ; File has been deleted. 164 | ; 165 | MSG_FILECOULDNOTBEDELETED 166 | File could not be deleted. 167 | ; File could not be deleted. 168 | ; 169 | MSG_VIRUSFOUNDETECTIONNAME 170 | Virus found in %s\nDetection name: %s\n\n 171 | ; Virus found in %s\nDetection name: %s\n\n 172 | ; 173 | MSG_GPL 174 | This program is free software; you can redistribute it and/or modify\nit under the terms of the GNU General Public License as published by\nthe Free Software Foundation; either version 2 of the \ 175 | License, or\n(at your option) any later version.\n\nThis program is distributed in the hope that it will be useful,\nbut WITHOUT ANY WARRANTY; without even the implied warranty of\nMERCHANTABILITY or \ 176 | FITNESS FOR A PARTICULAR PURPOSE. See the\nGNU General Public License for more details. 177 | ; This program is free software; you can redistribute it and/or modify\nit under the terms of the GNU General Public License as published by\nthe Free Software Foundation; either version 2 of the License, or\n(at your option) any later version.\n\nThis program is distributed in the hope that it will be useful,\nbut WITHOUT ANY WARRANTY; without even the implied warranty of\nMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\nGNU General Public License for more details. 178 | ; 179 | MSG_UNABLETOOPENREQUESTERTOSHOWERRORS 180 | Unable to open requester to show error;\n%s [%s]\n 181 | ; Unable to open requester to show error;\n%s [%s]\n 182 | ; 183 | MSG_UNABLETOOPENLIBRARY 184 | Unable to open %s v%d\n 185 | ; Unable to open %s v%d\n 186 | ; 187 | MSG_AREYOUSUREYOUWANTTOEXIT 188 | Are you sure you want to exit? 189 | ; Are you sure you want to exit? 190 | ; 191 | MSG_YESNO 192 | _Yes|_No 193 | ; _Yes|_No 194 | ; 195 | MSG_YESYESTOALLNONOTOALLABORT 196 | _Yes|Yes to _all|_No|N_o to all|Abort 197 | ; _Yes|Yes to _all|_No|N_o to all|Abort 198 | ; 199 | MSG_ARCHIVEISENCRYPTEDPLEASEENTERPASSWORD 200 | Archive is encrypted, please enter password. 201 | ; Archive is encrypted, please enter password. 202 | ; 203 | MSG_OKCANCEL 204 | _OK|_Cancel 205 | ; _OK|_Cancel 206 | ; 207 | MSG_UNABLETOOPENREQUESTERTOASKPASSWORD 208 | Unable to open requester to ask password\n 209 | ; Unable to open requester to ask password\n 210 | MSG_INTERFACE 211 | (interface) 212 | ; (interface) 213 | ; 214 | MSG_IGNOREFILESYSTEMS 215 | Ignore filesystems 216 | ; Ignore filesystems 217 | ; 218 | MSG_CXDESCRIPTION 219 | Unarchive GUI for XAD/XFD 220 | ; Unarchive GUI for XAD/XFD 221 | ; 222 | MSG_APPMENU_EXTRACTHERE 223 | Extract here 224 | ; Extract here 225 | ; 226 | MSG_SNAPSHOT 227 | Snapshot window 228 | ; Snapshot window 229 | ; 230 | MSG_UNABLETOOPENFILE 231 | Unable to open file 232 | ; Unable to open file 233 | ; 234 | MSG_OUTOFMEMORY 235 | Not enough memory 236 | ; Not enough memory 237 | ; 238 | MSG_LASTWINDOWCLOSED 239 | Last window closed. 240 | ; Last window closed. 241 | ; 242 | MSG_QUITHIDECANCEL 243 | Quit|Hide|Cancel 244 | ; Quit|Hide|Cancel 245 | ; 246 | MSG_NEWWINDOW 247 | New window... 248 | ; New window... 249 | ; 250 | MSG_QUITCFG_ASK 251 | Ask 252 | ; Ask 253 | ; 254 | MSG_QUITCFG_QUIT 255 | Quit 256 | ; Quit 257 | ; 258 | MSG_QUITCFG_HIDE 259 | Hide 260 | ; Hide 261 | ; 262 | MSG_LASTWINDOWACTION 263 | When last window closed: 264 | ; When last window closed: 265 | ; 266 | MSG_ADDFILES 267 | Add files... 268 | ; Add files... 269 | ; 270 | MSG_DELFILES 271 | Delete selected items... 272 | ; Delete selected items... 273 | ; 274 | MSG_UNABLETOOPENZIP 275 | Unable to open Zip for writing 276 | ; Unable to open Zip for writing 277 | ; 278 | MSG_LHAERROR 279 | Error processing file: %s 280 | ; Error processing file: %s 281 | ; 282 | MSG_SKIPRETRYABORT 283 | Skip|Retry|Abort 284 | ; Skip|Retry|Abort 285 | ; 286 | MSG_ARCHIVEMUSTHAVEENTRIES 287 | Archive must contain at least one file. 288 | ; Archive must contain at least one file. 289 | ; 290 | MSG_CONFIRMDELETE 291 | Are you sure you want to delete the selected entries? 292 | ; Are you sure you want to delete the selected entries? 293 | ; 294 | MSG_VIEWMODEBROWSER 295 | Browser 296 | ; Browser 297 | ; 298 | MSG_VIEWMODELIST 299 | List 300 | ; List 301 | ; 302 | MSG_VIEWMODE 303 | View mode 304 | ; View mode 305 | ; 306 | MSG_ERR_TREE_ALLOC 307 | Tree entries exceed allocated memory 308 | ; Tree entries exceed allocated memory 309 | ; 310 | MSG_NEWARCHIVE 311 | New archive... 312 | ; New archive... 313 | ; 314 | MSG_TYPE 315 | _Type 316 | ; _Type 317 | ; 318 | MSG_CREATE 319 | _Create 320 | ; _Create 321 | ; 322 | MSG_DIR 323 | (dir) 324 | ; (dir) 325 | ; 326 | MSG_PARENT 327 | (parent) 328 | ; (parent) 329 | ; 330 | MSG_PACKEDSIZE 331 | Packed Size 332 | ; Packed Size 333 | ; 334 | MSG_SNAPSHOT_WARNING 335 | This will not be persistent until prefs are saved! 336 | ; This will not be persistent until prefs are saved! 337 | ; 338 | MSG_ERR_NOTCPIP 339 | Please start your TCP/IP stack 340 | ; Please start your TCP/IP stack 341 | ; 342 | MSG_ERR_AMISSL 343 | Unable to open AmiSSL v5 344 | ; Unable to open AmiSSL v5 345 | ; 346 | MSG_ERR_UNKNOWN 347 | Unknown error 348 | ; Unknown error 349 | ; 350 | MSG_NEWVERSION 351 | New version (%s) available 352 | ; New version (%s) available 353 | ; 354 | MSG_NONEWVERSION 355 | Current version is up-to-date 356 | ; Current version is up-to-date 357 | ; 358 | MSG_CHECKVERSION 359 | Check for update... 360 | ; Check for update... 361 | ; 362 | -------------------------------------------------------------------------------- /libs/xvs.l.main: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/chris-y/avalanche/d32bc64424e88d857c8db56bfef035dfc7af7316/libs/xvs.l.main -------------------------------------------------------------------------------- /src/Avalanche_rev.h: -------------------------------------------------------------------------------- 1 | #define VERSION 2 2 | #define REVISION 4 3 | #define DATE "22.9.2023" 4 | #define VERS "Avalanche 2.4" 5 | #define VSTRING "Avalanche 2.4 (22.9.2023)\r\n" 6 | #define VERSTAG "\0$VER: Avalanche 2.4 (22.9.2023)" 7 | -------------------------------------------------------------------------------- /src/Avalanche_rev.i: -------------------------------------------------------------------------------- 1 | VERSION EQU 2 2 | REVISION EQU 4 3 | 4 | DATE MACRO 5 | dc.b '22.9.2023' 6 | ENDM 7 | 8 | VERS MACRO 9 | dc.b 'Avalanche 2.4' 10 | ENDM 11 | 12 | VSTRING MACRO 13 | dc.b 'Avalanche 2.4 (22.9.2023)',13,10,0 14 | ENDM 15 | 16 | VERSTAG MACRO 17 | dc.b 0,'$VER: Avalanche 2.4 (22.9.2023)',0 18 | ENDM 19 | -------------------------------------------------------------------------------- /src/Avalanche_rev.rev: -------------------------------------------------------------------------------- 1 | 4 2 | -------------------------------------------------------------------------------- /src/Avalanche_rev.s: -------------------------------------------------------------------------------- 1 | VERSION = 2 2 | REVISION = 4 3 | 4 | .macro DATE 5 | .ascii "22.9.2023" 6 | .endm 7 | 8 | .macro VERS 9 | .ascii "Avalanche 2.4" 10 | .endm 11 | 12 | .macro VSTRING 13 | .ascii "Avalanche 2.4 (22.9.2023)" 14 | .byte 13,10,0 15 | .endm 16 | 17 | .macro VERSTAG 18 | .byte 0 19 | .ascii "$VER: Avalanche 2.4 (22.9.2023)" 20 | .byte 0 21 | .endm 22 | -------------------------------------------------------------------------------- /src/Makefile: -------------------------------------------------------------------------------- 1 | all: install 2 | 3 | Avalanche: locale_strings.h 4 | make -C os3 5 | 6 | AvalanchePPC: locale_strings.h 7 | make -C os4 8 | 9 | locale_strings.h: ../catalogs/avalanche.cd 10 | catcomp /catalogs/avalanche.cd CFILE locale_strings.h NOCODE NOARRAY 11 | 12 | install: Avalanche AvalanchePPC 13 | copy os3/Avalanche / 14 | copy os4/AvalanchePPC / 15 | 16 | distrib: install 17 | makedir RAM:Avalanche 18 | copy //Avalanche.info RAM: 19 | copy /Avalanche#? RAM:Avalanche 20 | copy /avalanche.readme#? RAM:Avalanche 21 | copy /Install#? RAM:Avalanche 22 | copy /LICENSE RAM:Avalanche 23 | copy /AutoInstall RAM: 24 | makedir RAM:Avalanche/libs 25 | copy /libs/#? RAM:Avalanche/libs 26 | makedir RAM:Avalanche/catalogs 27 | copy /catalogs/#? RAM:Avalanche/catalogs 28 | lha a ram:avalanche.lha ram:Avalanche ram:Avalanche.info ram:AutoInstall 29 | 30 | clean: 31 | make -i -C os3 clean 32 | make -i -C os4 clean 33 | delete locale_strings.h 34 | 35 | version: 36 | bumprev 2 Avalanche 37 | -------------------------------------------------------------------------------- /src/arexx.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | 18 | #include 19 | #include 20 | 21 | #ifndef __amigaos4__ 22 | #include 23 | #endif 24 | 25 | #include 26 | 27 | #include "arexx.h" 28 | #include "avalanche.h" 29 | #include "libs.h" 30 | #include "misc.h" 31 | #include "Avalanche_rev.h" 32 | 33 | #include 34 | #include 35 | #include 36 | 37 | enum 38 | { 39 | RX_OPEN=0, 40 | RX_SHOW, 41 | RX_VERSION, 42 | }; 43 | 44 | static Object *arexx_obj = NULL; 45 | STATIC char result[100]; 46 | static ULONG event = RXEVT_NONE; 47 | static char *event_param = NULL; 48 | 49 | #ifdef __amigaos4__ 50 | #define RXHOOKF(func) static VOID func(struct ARexxCmd *cmd, struct RexxMsg *rxm __attribute__((unused))) 51 | #else 52 | #ifndef ASM 53 | #define ASM 54 | #endif 55 | 56 | #ifndef REG 57 | #define REG(reg,arg) __reg(#reg) arg 58 | #endif 59 | 60 | #define IDoMethod DoMethod 61 | #define IDoMethodA DoMethodA 62 | 63 | #define RXHOOKF(func) static ASM VOID func(REG(a0, struct ARexxCmd* cmd), REG(a1, struct RexxMsg* msg)) 64 | #endif 65 | 66 | RXHOOKF(rx_open); 67 | RXHOOKF(rx_show); 68 | RXHOOKF(rx_version); 69 | 70 | STATIC struct ARexxCmd Commands[] = 71 | { 72 | {"OPEN", RX_OPEN, rx_open, "FILE/A", 0, NULL, 0, 0, NULL }, 73 | {"SHOW", RX_SHOW, rx_show, NULL, 0, NULL, 0, 0, NULL }, 74 | {"VERSION", RX_VERSION, rx_version, NULL, 0, NULL, 0, 0, NULL }, 75 | { NULL, 0, NULL, NULL, 0, NULL, 0, 0, NULL } 76 | }; 77 | 78 | BOOL ami_arexx_init(ULONG *rxsig) 79 | { 80 | if((arexx_obj = ARexxObj, 81 | AREXX_HostName, "AVALANCHE", 82 | AREXX_Commands, Commands, 83 | AREXX_NoSlot, TRUE, 84 | AREXX_ReplyHook, NULL, 85 | AREXX_DefExtension, "arx", 86 | End)) 87 | { 88 | GetAttr(AREXX_SigMask, arexx_obj, rxsig); 89 | return TRUE; 90 | } 91 | else 92 | { 93 | /* Create a temporary ARexx port so we can send commands to existing */ 94 | arexx_obj = ARexxObj, 95 | AREXX_HostName, "AVALANCHE", 96 | AREXX_Commands, Commands, 97 | AREXX_NoSlot, FALSE, 98 | AREXX_ReplyHook, NULL, 99 | AREXX_DefExtension, "arx", 100 | End; 101 | 102 | return FALSE; 103 | } 104 | } 105 | 106 | ULONG ami_arexx_handle(void) 107 | { 108 | RA_HandleRexx(arexx_obj); 109 | 110 | return event; 111 | } 112 | 113 | static void ami_arexx_command(const char *cmd, const char *port) 114 | { 115 | if(arexx_obj == NULL) return; 116 | IDoMethod(arexx_obj, AM_EXECUTE, cmd, port, NULL, NULL, NULL, NULL); 117 | } 118 | 119 | void ami_arexx_send(const char *cmd) 120 | { 121 | ami_arexx_command(cmd, "AVALANCHE"); 122 | } 123 | 124 | void ami_arexx_cleanup(void) 125 | { 126 | if(arexx_obj) DisposeObject(arexx_obj); 127 | } 128 | 129 | void arexx_free_event(void) 130 | { 131 | if(event_param) free(event_param); 132 | event_param = NULL; 133 | event = RXEVT_NONE; 134 | } 135 | 136 | static void arexx_set_event(ULONG evt, char *param) 137 | { 138 | if(event_param) { 139 | arexx_free_event(); 140 | event_param = NULL; 141 | } 142 | if(param) event_param = strdup(param); 143 | event = evt; 144 | } 145 | 146 | char *arexx_get_event(void) 147 | { 148 | return event_param; 149 | } 150 | 151 | 152 | RXHOOKF(rx_open) 153 | { 154 | cmd->ac_RC = 0; 155 | 156 | arexx_set_event(RXEVT_OPEN, (char *)cmd->ac_ArgList[0]); 157 | } 158 | 159 | RXHOOKF(rx_show) 160 | { 161 | cmd->ac_RC = 0; 162 | 163 | arexx_set_event(RXEVT_SHOW, NULL); 164 | } 165 | 166 | RXHOOKF(rx_version) 167 | { 168 | static char reply[10]; 169 | cmd->ac_RC = 0; 170 | snprintf(reply, sizeof(reply), "%d.%d", VERSION, REVISION); 171 | cmd->ac_Result = reply; 172 | } 173 | -------------------------------------------------------------------------------- /src/arexx.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef AREXX_H 16 | #define AREXX_H 17 | 18 | #include 19 | 20 | enum { 21 | RXEVT_NONE = 0, 22 | RXEVT_OPEN, 23 | RXEVT_SHOW 24 | }; 25 | 26 | BOOL ami_arexx_init(ULONG *rxsig); 27 | ULONG ami_arexx_handle(void); 28 | void ami_arexx_send(const char *); 29 | void ami_arexx_cleanup(void); 30 | 31 | char *arexx_get_event(void); 32 | void arexx_free_event(void); 33 | #endif 34 | -------------------------------------------------------------------------------- /src/avalanche.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef AVALANCHE_H 16 | #define AVALANCHE_H 1 17 | 18 | #include 19 | 20 | struct avalanche_config; 21 | 22 | #define PROGRESS_SIZE_DEFAULT 20 23 | 24 | #ifndef MEMF_PRIVATE 25 | #define MEMF_PRIVATE 0L 26 | #endif 27 | 28 | extern const ULONG zero; 29 | 30 | #define ARC_NONE 0 31 | #define ARC_XAD 1 32 | #define ARC_XFD 2 33 | #define ARC_DEARK 4 34 | 35 | enum { 36 | WIN_DONE_OK = 0, 37 | WIN_DONE_CLOSED, 38 | WIN_DONE_QUIT, 39 | }; 40 | 41 | struct avalanche_config *get_config(void); 42 | ULONG ask_quit(void *awin); 43 | void savesettings(Object *win); 44 | long extract(void *awin, char *archive, char *newdest, struct Node *node); 45 | void free_dest_path(void); 46 | 47 | /* window list */ 48 | void add_to_window_list(void *awin); 49 | void del_from_window_list(void *awin); 50 | 51 | #endif 52 | -------------------------------------------------------------------------------- /src/config.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | #include 18 | 19 | #include 20 | #include 21 | #include 22 | #include 23 | #include 24 | 25 | #ifndef __amigaos4__ 26 | #include 27 | #endif 28 | #include 29 | 30 | #include 31 | #include 32 | #include 33 | #include 34 | #include 35 | #include 36 | #include 37 | 38 | #include 39 | #include 40 | #include 41 | #include 42 | #include 43 | 44 | #include 45 | #include 46 | 47 | #include "avalanche.h" 48 | #include "config.h" 49 | #include "libs.h" 50 | #include "locale.h" 51 | 52 | #include "Avalanche_rev.h" 53 | 54 | enum { 55 | GID_C_MAIN = 0, 56 | GID_C_SCAN, 57 | GID_C_IGNOREFS, 58 | GID_C_DEST, 59 | GID_C_VIEWMODE, 60 | GID_C_QUIT, 61 | GID_C_SAVE, 62 | GID_C_USE, 63 | GID_C_CANCEL, 64 | GID_C_LAST 65 | }; 66 | 67 | enum { 68 | WID_MAIN = 0, 69 | WID_LAST 70 | }; 71 | 72 | enum { 73 | OID_MAIN = 0, 74 | OID_LAST 75 | }; 76 | 77 | static struct Window *windows[WID_LAST]; 78 | static struct Gadget *gadgets[GID_C_LAST]; 79 | static Object *objects[OID_LAST]; 80 | static struct MsgPort *cw_port = NULL; 81 | 82 | static void config_window_close(void) 83 | { 84 | RA_CloseWindow(objects[OID_MAIN]); 85 | windows[WID_MAIN] = NULL; 86 | DisposeObject(objects[OID_MAIN]); 87 | 88 | DeleteMsgPort(cw_port); 89 | cw_port = NULL; 90 | } 91 | 92 | static void config_req_dest(void) 93 | { 94 | DoMethod((Object *)gadgets[GID_C_DEST], GFILE_REQUEST, windows[WID_MAIN]); 95 | } 96 | 97 | static void config_save(struct avalanche_config *config) 98 | { 99 | struct DiskObject *dobj; 100 | UBYTE **oldtooltypes; 101 | UBYTE *newtooltypes[21]; 102 | char tt_dest[100]; 103 | char tt_srcdir[100]; 104 | char tt_tmp[100]; 105 | char tt_winx[15]; 106 | char tt_winy[15]; 107 | char tt_winh[15]; 108 | char tt_winw[15]; 109 | char tt_progresssize[20]; 110 | char tt_cxpri[20]; 111 | char tt_cxpopkey[50]; 112 | char tt_modules[40]; 113 | 114 | if(dobj = GetIconTagList(config->progname, NULL)) { 115 | oldtooltypes = (UBYTE **)dobj->do_ToolTypes; 116 | 117 | if(config->dest && (strcmp("RAM:", config->dest) != 0)) { 118 | snprintf(tt_dest, 100, "DEST=%s", config->dest); 119 | newtooltypes[0] = tt_dest; 120 | } else { 121 | newtooltypes[0] = "(DEST=RAM:)"; 122 | } 123 | 124 | if(config->viewmode == 1) { 125 | newtooltypes[1] = "VIEWMODE=LIST"; 126 | } else { 127 | newtooltypes[1] = "(VIEWMODE=LIST|BROWSER)"; 128 | } 129 | 130 | if(config->disable_asl_hook) { 131 | newtooltypes[2] = "NOASLHOOK"; 132 | } else { 133 | newtooltypes[2] = "(NOASLHOOK)"; 134 | } 135 | 136 | if(config->win_x) { 137 | snprintf(tt_winx, 15, "WINX=%lu", config->win_x); 138 | newtooltypes[3] = tt_winx; 139 | } else { 140 | newtooltypes[3] = "(WINX=0)"; 141 | } 142 | 143 | if(config->win_y) { 144 | snprintf(tt_winy, 15,"WINY=%lu", config->win_y); 145 | newtooltypes[4] = tt_winy; 146 | } else { 147 | newtooltypes[4] = "(WINY=0)"; 148 | } 149 | 150 | if(config->win_w) { 151 | snprintf(tt_winw, 15, "WINW=%lu", config->win_w); 152 | newtooltypes[5] = tt_winw; 153 | } else { 154 | newtooltypes[5] = "(WINW=0)"; 155 | } 156 | 157 | if(config->win_h) { 158 | snprintf(tt_winh, 15, "WINH=%lu", config->win_h); 159 | newtooltypes[6] = tt_winh; 160 | } else { 161 | newtooltypes[6] = "(WINH=0)"; 162 | } 163 | 164 | if(config->progress_size != PROGRESS_SIZE_DEFAULT) { 165 | snprintf(tt_progresssize, 20, "PROGRESSSIZE=%lu", config->progress_size); 166 | } else { 167 | snprintf(tt_progresssize, 20, "(PROGRESSSIZE=%d)", PROGRESS_SIZE_DEFAULT); 168 | } 169 | 170 | newtooltypes[7] = tt_progresssize; 171 | 172 | if(config->virus_scan) { 173 | newtooltypes[8] = "VIRUSSCAN"; 174 | } else { 175 | newtooltypes[8] = "(VIRUSSCAN)"; 176 | } 177 | 178 | switch(config->closeaction) { 179 | case 1: 180 | newtooltypes[9] = "CLOSE=QUIT"; 181 | break; 182 | case 2: 183 | newtooltypes[9] = "CLOSE=HIDE"; 184 | break; 185 | case 0: 186 | newtooltypes[9] = "CLOSE=ASK"; 187 | break; 188 | } 189 | 190 | if(config->ignorefs) { 191 | newtooltypes[10] = "IGNOREFS"; 192 | } else { 193 | newtooltypes[10] = "(IGNOREFS)"; 194 | } 195 | 196 | if(config->tmpdir && (strncmp("T:", config->tmpdir, config->tmpdirlen) != 0)) { 197 | strcpy(tt_tmp, "TMPDIR="); 198 | newtooltypes[11] = strncat(tt_tmp, config->tmpdir, config->tmpdirlen); 199 | } else { 200 | newtooltypes[11] = "(TMPDIR=T:)"; 201 | } 202 | 203 | if(config->cx_popup == FALSE) { 204 | newtooltypes[12] = "CX_POPUP=NO"; 205 | } else { 206 | newtooltypes[12] = "(CX_POPUP=YES)"; 207 | } 208 | 209 | if(config->cx_pri != 0) { 210 | snprintf(tt_cxpri, 20, "CX_PRIORITY=%d", config->cx_pri); 211 | } else { 212 | snprintf(tt_cxpri, 20, "(CX_PRIORITY=0)"); 213 | } 214 | newtooltypes[13] = tt_cxpri; 215 | 216 | if((config->cx_popkey) && (strcmp(config->cx_popkey, "rawkey ctrl alt a") != 0)) { 217 | snprintf(tt_cxpopkey, 50, "CX_POPKEY=%s", config->cx_popkey + 7); 218 | } else { 219 | snprintf(tt_cxpopkey, 50, "(CX_POPKEY=ctrl alt a)"); 220 | } 221 | newtooltypes[14] = tt_cxpopkey; 222 | 223 | newtooltypes[15] = "DONOTWAIT"; 224 | 225 | if(config->sourcedir && (strcmp("RAM:", config->sourcedir) != 0)) { 226 | snprintf(tt_srcdir, 100, "SOURCEDIR=%s", config->sourcedir); 227 | newtooltypes[16] = tt_srcdir; 228 | 229 | } else { 230 | newtooltypes[16] = "(SOURCEDIR=RAM:)"; 231 | } 232 | 233 | if(config->drag_lock) { 234 | newtooltypes[17] = "DRAGLOCK"; 235 | } else { 236 | newtooltypes[17] = "(DRAGLOCK)"; 237 | } 238 | 239 | if(config->aiss) { 240 | newtooltypes[18] = "AISS"; 241 | } else { 242 | newtooltypes[18] = "(AISS)"; 243 | } 244 | 245 | if(config->activemodules == (ARC_XAD | ARC_XFD)) { 246 | snprintf(tt_modules, 40, "(MODULES=XAD|XFD|DEARK)"); 247 | } else { 248 | snprintf(tt_modules, 40, "MODULES="); 249 | if(config->activemodules & ARC_XAD) { 250 | strncat(tt_modules, "XAD", 40); 251 | if((config->activemodules & ARC_XFD) || (config->activemodules & ARC_DEARK)) { 252 | strncat(tt_modules, "|", 40); 253 | } 254 | } 255 | if(config->activemodules & ARC_XFD) { 256 | strncat(tt_modules, "XFD", 40); 257 | if((config->activemodules & ARC_DEARK)) { 258 | strncat(tt_modules, "|", 40); 259 | } 260 | } 261 | if(config->activemodules & ARC_DEARK) { 262 | strncat(tt_modules, "DEARK", 40); 263 | } 264 | } 265 | newtooltypes[19] = tt_modules; 266 | 267 | newtooltypes[20] = NULL; 268 | 269 | dobj->do_ToolTypes = (STRPTR *)&newtooltypes; 270 | PutIconTags(config->progname, dobj, NULL); 271 | dobj->do_ToolTypes = (STRPTR *)oldtooltypes; 272 | FreeDiskObject(dobj); 273 | } 274 | } 275 | 276 | static void config_window_settings(struct avalanche_config *config, BOOL save) 277 | { 278 | ULONG data = 0; 279 | #if 0 280 | free_dest_path(); 281 | GetAttr(GETFILE_Drawer, gadgets[GID_C_DEST], (APTR)&config->dest); 282 | #endif 283 | GetAttr(GA_Selected, gadgets[GID_C_SCAN],(ULONG *)&data); 284 | config->virus_scan = (data ? TRUE : FALSE); 285 | 286 | GetAttr(GA_Selected, gadgets[GID_C_IGNOREFS],(ULONG *)&data); 287 | config->ignorefs = (data ? TRUE : FALSE); 288 | 289 | GetAttr(CHOOSER_Selected, gadgets[GID_C_QUIT], (ULONG *)&data); 290 | config->closeaction = data; 291 | 292 | GetAttr(CHOOSER_Selected, gadgets[GID_C_VIEWMODE], (ULONG *)&data); 293 | config->viewmode = data; 294 | 295 | if(save) config_save(config); 296 | } 297 | 298 | /* Public functions */ 299 | void config_window_open(struct avalanche_config *config) 300 | { 301 | BOOL save_disabled = FALSE; 302 | STRPTR quit_opts[] = { 303 | locale_get_string(MSG_QUITCFG_ASK), 304 | locale_get_string(MSG_QUITCFG_QUIT), 305 | locale_get_string(MSG_QUITCFG_HIDE), 306 | NULL 307 | }; 308 | 309 | STRPTR viewmode_opts[] = { 310 | locale_get_string(MSG_VIEWMODEBROWSER), 311 | locale_get_string(MSG_VIEWMODELIST), 312 | NULL 313 | }; 314 | 315 | if(windows[WID_MAIN]) { // already open 316 | WindowToFront(windows[WID_MAIN]); 317 | return; 318 | } 319 | 320 | if(config->progname == NULL) save_disabled = TRUE; 321 | 322 | if(cw_port = CreateMsgPort()) { 323 | /* Create the window object */ 324 | objects[OID_MAIN] = WindowObj, 325 | WA_ScreenTitle, VERS, 326 | WA_Title, VERS, 327 | WA_Activate, TRUE, 328 | WA_DepthGadget, TRUE, 329 | WA_DragBar, TRUE, 330 | WA_CloseGadget, TRUE, 331 | WA_SizeGadget, FALSE, 332 | WINDOW_SharedPort, cw_port, 333 | WINDOW_Position, WPOS_CENTERSCREEN, 334 | WINDOW_ParentGroup, gadgets[GID_C_MAIN] = LayoutVObj, 335 | //LAYOUT_DeferLayout, TRUE, 336 | LAYOUT_SpaceOuter, TRUE, 337 | LAYOUT_AddChild, LayoutVObj, 338 | #if 0 339 | LAYOUT_AddChild, gadgets[GID_C_DEST] = GetFileObj, 340 | GA_ID, GID_C_DEST, 341 | GA_RelVerify, TRUE, 342 | GETFILE_TitleText, locale_get_string( MSG_SELECTDESTINATION ) , 343 | GETFILE_Drawer, config->dest, 344 | GETFILE_DoSaveMode, TRUE, 345 | GETFILE_DrawersOnly, TRUE, 346 | GETFILE_ReadOnly, TRUE, 347 | End, 348 | CHILD_WeightedHeight, 0, 349 | CHILD_Label, LabelObj, 350 | LABEL_Text, locale_get_string( MSG_DESTINATION ) , 351 | LabelEnd, 352 | #endif 353 | LAYOUT_AddChild, gadgets[GID_C_SCAN] = CheckBoxObj, 354 | GA_ID, GID_C_SCAN, 355 | GA_RelVerify, TRUE, 356 | GA_Disabled, config->disable_vscan_menu, 357 | GA_Text, locale_get_string( MSG_SCANFORVIRUSES ) , 358 | GA_Selected, config->virus_scan, 359 | End, 360 | LAYOUT_AddChild, gadgets[GID_C_IGNOREFS] = CheckBoxObj, 361 | GA_ID, GID_C_IGNOREFS, 362 | GA_RelVerify, TRUE, 363 | GA_Text, locale_get_string( MSG_IGNOREFILESYSTEMS ) , 364 | GA_Selected, config->ignorefs, 365 | End, 366 | LAYOUT_AddChild, gadgets[GID_C_VIEWMODE] = ChooserObj, 367 | GA_ID, GID_C_VIEWMODE, 368 | GA_RelVerify, TRUE, 369 | CHOOSER_Selected, config->viewmode, 370 | CHOOSER_PopUp, TRUE, 371 | CHOOSER_LabelArray, viewmode_opts, 372 | End, 373 | CHILD_Label, LabelObj, 374 | LABEL_Text, locale_get_string(MSG_VIEWMODE), 375 | LabelEnd, 376 | LAYOUT_AddChild, gadgets[GID_C_QUIT] = ChooserObj, 377 | GA_ID, GID_C_QUIT, 378 | GA_RelVerify, TRUE, 379 | CHOOSER_Selected, config->closeaction, 380 | CHOOSER_PopUp, TRUE, 381 | CHOOSER_LabelArray, quit_opts, 382 | End, 383 | CHILD_Label, LabelObj, 384 | LABEL_Text, locale_get_string(MSG_LASTWINDOWACTION), 385 | LabelEnd, 386 | LAYOUT_AddChild, LayoutHObj, 387 | LAYOUT_AddChild, gadgets[GID_C_SAVE] = ButtonObj, 388 | GA_ID, GID_C_SAVE, 389 | GA_RelVerify, TRUE, 390 | GA_Text, locale_get_string( MSG_SAVE ), 391 | GA_Disabled, save_disabled, 392 | ButtonEnd, 393 | LAYOUT_AddChild, gadgets[GID_C_USE] = ButtonObj, 394 | GA_ID, GID_C_USE, 395 | GA_RelVerify, TRUE, 396 | GA_Text, locale_get_string( MSG_USE ), 397 | ButtonEnd, 398 | LAYOUT_AddChild, gadgets[GID_C_CANCEL] = ButtonObj, 399 | GA_ID, GID_C_CANCEL, 400 | GA_RelVerify, TRUE, 401 | GA_Text, locale_get_string( MSG_CANCEL ), 402 | ButtonEnd, 403 | CHILD_WeightedHeight, 0, 404 | LayoutEnd, 405 | LayoutEnd, 406 | EndGroup, 407 | EndWindow; 408 | 409 | if(objects[OID_MAIN]) { 410 | windows[WID_MAIN] = (struct Window *)RA_OpenWindow(objects[OID_MAIN]); 411 | } 412 | } 413 | 414 | return; 415 | } 416 | 417 | ULONG config_window_get_signal(void) 418 | { 419 | if(cw_port) { 420 | return (1L << cw_port->mp_SigBit); 421 | } else { 422 | return 0; 423 | } 424 | } 425 | 426 | ULONG config_window_handle_input(UWORD *code) 427 | { 428 | return RA_HandleInput(objects[OID_MAIN], code); 429 | } 430 | 431 | BOOL config_window_handle_input_events(struct avalanche_config *config, ULONG result, UWORD code) 432 | { 433 | long ret = 0; 434 | ULONG done = FALSE; 435 | 436 | switch (result & WMHI_CLASSMASK) { 437 | case WMHI_CLOSEWINDOW: 438 | config_window_close(); 439 | done = TRUE; 440 | break; 441 | 442 | case WMHI_GADGETUP: 443 | switch (result & WMHI_GADGETMASK) { 444 | case GID_C_DEST: 445 | config_req_dest(); 446 | break; 447 | case GID_C_SAVE: 448 | config_window_settings(config, TRUE); 449 | config_window_close(); 450 | done = TRUE; 451 | break; 452 | case GID_C_USE: 453 | config_window_settings(config, FALSE); 454 | // fall through 455 | case GID_C_CANCEL: 456 | config_window_close(); 457 | done = TRUE; 458 | break; 459 | } 460 | break; 461 | } 462 | 463 | return done; 464 | } 465 | -------------------------------------------------------------------------------- /src/config.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef AVALANCHE_CONFIG_H 16 | #define AVALANCHE_CONFIG_H 1 17 | 18 | struct avalanche_config { 19 | char *progname; 20 | 21 | char *sourcedir; /* default source dir for ASL */ 22 | char *dest; /* default destination */ 23 | char *tmpdir; 24 | int tmpdirlen; 25 | 26 | BOOL disable_asl_hook; 27 | ULONG viewmode; /* [1 = list, 0 = browser] */ 28 | BOOL virus_scan; 29 | BOOL debug; 30 | BOOL ignorefs; 31 | BOOL disable_vscan_menu; 32 | BOOL drag_lock; 33 | BOOL aiss; 34 | ULONG closeaction; /* [1 = quit, 2 = hide, 0 = cancel] -- same as quit req */ 35 | ULONG activemodules; 36 | 37 | ULONG win_x; 38 | ULONG win_y; 39 | ULONG win_w; 40 | ULONG win_h; 41 | ULONG progress_size; 42 | 43 | int cx_pri; 44 | BOOL cx_popup; 45 | char *cx_popkey; 46 | }; 47 | 48 | void config_window_open(struct avalanche_config *config); 49 | ULONG config_window_get_signal(void); 50 | ULONG config_window_handle_input(UWORD *code); 51 | BOOL config_window_handle_input_events(struct avalanche_config *config, ULONG result, UWORD code); 52 | 53 | #endif 54 | -------------------------------------------------------------------------------- /src/deark.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | 18 | #include 19 | 20 | #include 21 | #include 22 | #include 23 | 24 | #include "avalanche.h" 25 | #include "config.h" 26 | #include "libs.h" 27 | #include "misc.h" 28 | #include "module.h" 29 | #include "win.h" 30 | #include "deark.h" 31 | 32 | #ifdef __amigaos4__ 33 | #define Seek ChangeFilePosition 34 | #endif 35 | 36 | enum { 37 | DEARK_RECOG, 38 | DEARK_LIST, 39 | DEARK_EXTRACT 40 | }; 41 | 42 | struct deark_userdata { 43 | char *file; 44 | char *tmpfile; 45 | char **list; 46 | long total; 47 | char *arctype; 48 | char *last_error; 49 | }; 50 | 51 | static void free_list(char **list, long items) 52 | { 53 | for(int i = 0; i < items; i++) { 54 | if(list[i]) FreeVec(list[i]); 55 | } 56 | 57 | if(list) FreeVec(list); 58 | } 59 | 60 | static void deark_free(void *awin) 61 | { 62 | struct deark_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 63 | 64 | if(du) { 65 | if(du->tmpfile) FreeVec(du->tmpfile); 66 | if(du->file) free(du->file); 67 | if(du->arctype) free(du->arctype); 68 | if(du->last_error) free(du->last_error); 69 | 70 | if(du->list) free_list(du->list, du->total); 71 | } 72 | 73 | window_free_archive_userdata(awin); 74 | } 75 | 76 | static const char *deark_error(void *awin, long code) 77 | { 78 | struct deark_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 79 | 80 | if(du == NULL) return NULL; 81 | 82 | return(du->last_error); 83 | } 84 | 85 | static long deark_send_command(void *awin, char *file, int command, char ***list, char *dest, long index) 86 | { 87 | BPTR fh = 0; 88 | int err = 1; 89 | char cmd[1024]; 90 | 91 | struct avalanche_config *config = get_config(); 92 | struct deark_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 93 | 94 | if(du == NULL) return -1; 95 | 96 | if(du->tmpfile == NULL) { 97 | du->tmpfile = AllocVec(config->tmpdirlen + 25, MEMF_CLEAR); 98 | if(du->tmpfile == NULL) return 0; 99 | 100 | strcpy(du->tmpfile, config->tmpdir); 101 | AddPart(du->tmpfile, "deark_tmp", config->tmpdirlen + 25); 102 | } 103 | 104 | switch(command) { 105 | case DEARK_LIST: 106 | snprintf(cmd, 1024, "deark -l -q \"%s\"", file); 107 | break; 108 | 109 | case DEARK_RECOG: 110 | snprintf(cmd, 1024, "deark -id \"%s\"", file); 111 | break; 112 | 113 | case DEARK_EXTRACT: 114 | snprintf(cmd, 1024, "deark -get %d -od \"%s\" -q \"%s\"", index, dest, file); 115 | break; 116 | 117 | default: 118 | return -1; 119 | break; 120 | } 121 | 122 | if(fh = Open(du->tmpfile, MODE_NEWFILE)) { 123 | err = SystemTags(cmd, 124 | SYS_Input, NULL, 125 | SYS_Output, fh, 126 | SYS_Error, NULL, 127 | NP_Name, "Avalanche Deark process", 128 | TAG_DONE); 129 | 130 | Close(fh); 131 | } 132 | 133 | // if(err == 0) { 134 | char *res; 135 | char buf[200]; 136 | ULONG i = 0; 137 | ULONG total = 0; 138 | 139 | if(fh = Open(du->tmpfile, MODE_OLDFILE)) { 140 | res = (char *)&buf; 141 | while(res != NULL) { 142 | res = FGets(fh, buf, 200); 143 | if(strncmp(buf, "Error: ", 7) == 0) { 144 | if(du->last_error) free(du->last_error); 145 | du->last_error = strdup(buf); 146 | Close(fh); 147 | if(!config->debug) DeleteFile(du->tmpfile); 148 | return -1; 149 | } 150 | if(res) total++; 151 | } 152 | 153 | *list = AllocVec(total, MEMF_CLEAR); 154 | 155 | Seek(fh, 0, OFFSET_BEGINNING); 156 | 157 | res = (char *)&buf; 158 | for(i = 0; i < total; i++) { 159 | res = FGets(fh, buf, 200); 160 | 161 | buf[strlen(buf) - 1] = '\0'; 162 | 163 | *list[i] = AllocVec(strlen(buf), MEMF_CLEAR); 164 | strcpy(*list[i], buf); 165 | 166 | } 167 | 168 | Close(fh); 169 | if(!config->debug) DeleteFile(du->tmpfile); 170 | return(total); 171 | } 172 | 173 | // } else return err; 174 | 175 | return 0; 176 | } 177 | 178 | static const char *deark_get_arc_format(void *awin) 179 | { 180 | struct deark_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 181 | if(!du) return NULL; 182 | 183 | return(du->arctype + 7); 184 | } 185 | 186 | static const char *deark_get_filename(void *userdata, void *awin) 187 | { 188 | struct deark_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 189 | 190 | if(du) { 191 | long i = (long)userdata; 192 | return du->list[i]; 193 | } 194 | 195 | return NULL; 196 | 197 | } 198 | 199 | long deark_info(char *file, struct avalanche_config *config, void *awin, void(*addnode)(char *name, LONG *size, BOOL dir, ULONG item, ULONG total, void *userdata, struct avalanche_config *config, void *awin)) 200 | { 201 | int err = 1; 202 | BPTR fh = 0; 203 | struct deark_userdata *du = (struct deark_userdata *)window_alloc_archive_userdata(awin, sizeof(struct deark_userdata)); 204 | if(du == NULL) return -1; 205 | 206 | du->file = strdup(file); 207 | 208 | char **list = NULL; 209 | long entries = deark_send_command(awin, file, DEARK_RECOG, &list, NULL, 0); 210 | if(entries > 0) { 211 | if(strncmp(list[0], "Module:", 7) == 0) { 212 | du->arctype = strdup(list[0]); 213 | free_list(list, entries); 214 | } else { 215 | return -1; 216 | } 217 | } 218 | 219 | du->total = deark_send_command(awin, file, DEARK_LIST, &du->list, NULL, 0); 220 | 221 | if(du->total > 0) { 222 | char *res; 223 | char buf[200]; 224 | ULONG i = 0; 225 | 226 | /* Add to list */ 227 | for(i = 0; i < du->total; i++) { 228 | addnode(du->list[i], &zero, 229 | FALSE, i, du->total, (void *)i, config, awin); 230 | i++; 231 | } 232 | 233 | return 0; 234 | } 235 | 236 | return err; 237 | } 238 | 239 | static long deark_extract_file_private(void *awin, char *dest, struct deark_userdata *du, long idx) 240 | { 241 | char **list = NULL; 242 | long err = 1; 243 | long entries = 0; 244 | if(idx < 0) return err; 245 | entries = deark_send_command(awin, du->file, DEARK_EXTRACT, &list, dest, idx); 246 | if(entries >= 0) { 247 | if(list) free_list(list, entries); 248 | return 0; 249 | } 250 | return err; 251 | } 252 | 253 | 254 | long deark_extract_file(void *awin, char *file, char *dest, struct Node *node, void *(getnode)(void *awin, struct Node *node)) 255 | { 256 | long err; 257 | struct deark_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 258 | long idx = (long)getnode(awin, node); 259 | 260 | return deark_extract_file_private(awin, dest, du, idx); 261 | } 262 | 263 | /* returns 0 on success */ 264 | long deark_extract(void *awin, char *file, char *dest, struct List *list, void *(getnode)(void *awin, struct Node *node)) 265 | { 266 | long err = 0; 267 | struct Node *fnode; 268 | 269 | struct desrk_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 270 | 271 | if(du) { 272 | for(fnode = list->lh_Head; fnode->ln_Succ; fnode=fnode->ln_Succ) { 273 | err = deark_extract_file(awin, file, dest, fnode, getnode); 274 | if(err != 0) { 275 | return err; 276 | } 277 | } 278 | } 279 | 280 | return err; 281 | } 282 | 283 | long deark_extract_array(void *awin, ULONG total_items, char *dest, void **array, void *(getuserdata)(void *awin, void *arc_entry)) 284 | { 285 | long err = 0; 286 | 287 | struct deark_userdata *du = (struct deark_userdata *)window_get_archive_userdata(awin); 288 | 289 | if(du) { 290 | for(int i = 0; i < total_items; i++) { 291 | long idx = (long)getuserdata(awin, array[i]); 292 | err = deark_extract_file_private(awin, dest, du, idx); 293 | if(err != 0) { 294 | return err; 295 | } 296 | } 297 | } 298 | 299 | return err; 300 | } 301 | 302 | void deark_register(struct module_functions *funcs) 303 | { 304 | funcs->module[0] = 'A'; 305 | funcs->module[1] = 'R'; 306 | funcs->module[2] = 'K'; 307 | funcs->module[3] = 0; 308 | 309 | funcs->get_filename = deark_get_filename; 310 | funcs->free = deark_free; 311 | funcs->get_format = deark_get_arc_format; 312 | funcs->get_subformat = NULL; 313 | funcs->get_error = deark_error; 314 | funcs->get_crunchsize = NULL; 315 | } 316 | -------------------------------------------------------------------------------- /src/deark.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef DEARK_H 16 | #define DEARK_H 1 17 | 18 | #include "avalanche.h" 19 | 20 | BOOL deark_recog(char *file); 21 | 22 | long deark_info(char *file, struct avalanche_config *config, void *awin, void(*addnode)(char *name, LONG *size, BOOL dir, ULONG item, ULONG total, void *userdata, struct avalanche_config *config, void *awin)); 23 | long deark_extract_array(void *awin, ULONG total_items, char *dest, void **array, void *(getuserdata)(void *awin, void *arc_entry)); 24 | long deark_extract(void *awin, char *file, char *dest, struct List *list, void *(getnode)(void *awin, struct Node *node)); 25 | long deark_extract_file(void *awin, char *file, char *dest, struct Node *node, void *(getnode)(void *awin, struct Node *node)); 26 | 27 | 28 | void deark_register(struct module_functions *funcs); 29 | #endif 30 | -------------------------------------------------------------------------------- /src/http.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | 17 | #include 18 | #include 19 | 20 | #ifdef __amigaos4__ 21 | #include 22 | #endif 23 | 24 | #include 25 | #include 26 | #include 27 | #include 28 | 29 | #ifndef __amigaos4__ 30 | #define AMISSL_INLINE_H 31 | #define _OPENSSL_init_ssl(opts, settings) OPENSSL_init_ssl(opts, settings) 32 | #endif 33 | 34 | #include 35 | #include 36 | #include 37 | #include 38 | #include 39 | 40 | struct Library *SocketBase; 41 | struct Library *AmiSSLMasterBase; 42 | 43 | #ifdef __amigaos4__ 44 | struct SocketIFace *ISocket; 45 | struct AmiSSLMasterIFace *IAmiSSLMaster; 46 | struct AmiSSLIFace *IAmiSSL; 47 | #else 48 | struct Library *AmiSSLBase = NULL; 49 | struct Library *AmiSSLExtBase = NULL; 50 | #endif 51 | 52 | #include "http.h" 53 | #include "locale.h" 54 | #include "misc.h" 55 | #include "req.h" 56 | 57 | #include "Avalanche_rev.h" 58 | 59 | enum { 60 | AHTTP_ERR_NONE = 0, 61 | AHTTP_ERR_NOTCPIP, 62 | AHTTP_ERR_AMISSL, 63 | AHTTP_ERR_UNKNOWN 64 | }; 65 | 66 | char *err_txt = NULL; 67 | 68 | void http_cleanup(void) 69 | { 70 | if(SocketBase) CloseLibrary(SocketBase); 71 | #ifdef __amigaos4__ 72 | if (ISocket) DropInterface((struct Interface *)ISocket); 73 | #endif 74 | } 75 | 76 | void http_closesocketlibs() 77 | { 78 | if(AmiSSLMasterBase) 79 | { 80 | CloseAmiSSL(); 81 | #ifdef __amigaos4__ 82 | if(IAmiSSLMaster) DropInterface((struct Interface *)IAmiSSLMaster); 83 | IAmiSSLMaster = NULL; 84 | #endif 85 | CloseLibrary((struct Library *)AmiSSLMasterBase); 86 | AmiSSLMasterBase = NULL; 87 | } 88 | 89 | #ifdef __amigaos4__ 90 | DropInterface((struct Interface *)ISocket); 91 | #endif 92 | CloseLibrary(SocketBase); 93 | SocketBase=NULL; 94 | } 95 | 96 | /* Required callback to enable HTTPS connection, when necessary 97 | */ 98 | SAVEDS STDARGS BIO *HTTP_TLS_cb(BIO *bio, void *arg, int connect, int detail) 99 | { 100 | if (connect && detail) 101 | { 102 | /* Connect with TLS */ 103 | BIO *sbio = BIO_new_ssl((SSL_CTX *)arg, 1); 104 | bio = (sbio != NULL) ? BIO_push(sbio, bio) : NULL; 105 | } 106 | 107 | return bio; 108 | } 109 | 110 | /* Stub function used when freeing our stack of headers 111 | */ 112 | SAVEDS STDARGS void stub_X509V3_conf_free(CONF_VALUE *val) 113 | { 114 | X509V3_conf_free(val); 115 | } 116 | 117 | static int err_cb(const char *str, size_t len, void *u) 118 | { 119 | #ifdef __amigaos4__ 120 | DebugPrintF("[Avalanche] %s\n", str); 121 | #endif 122 | 123 | err_txt = strdup(str); 124 | 125 | return 1; 126 | } 127 | 128 | static BOOL http_get_url(char *url, SSL_CTX *sslctx, char *buffer, ULONG bufsize) 129 | { 130 | STACK_OF(CONF_VALUE) *headers = NULL; 131 | BIO *bio, *bio_err; 132 | ULONG length; 133 | char app[50]; 134 | 135 | /* Allow unsafe legacy renegotiation */ 136 | //SSL_CTX_set_options(sslctx, SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION); 137 | 138 | /* Add our own HTTP headers */ 139 | snprintf(app, 49, "Avalanche/%d.%d", VERSION, REVISION); 140 | X509V3_add_value("User-Agent", app, &headers); 141 | 142 | /* Initiate the request (supports redirection) */ 143 | if ((bio = OSSL_HTTP_get(url, NULL /* proxy */, NULL /* no_proxy */, 144 | NULL /* bio */, NULL /* rbio */, 145 | (BIO *(*)(BIO *, void *, int, int))HTTP_TLS_cb, sslctx, 146 | 0 /* buf_size */, headers, 147 | NULL /* expected_content_type */, 0 /* expect_asn1 */, 148 | 0 /* max_resp_len */, 60 /* timeout */)) != NULL) 149 | { 150 | /* HTTP request succeeded */ 151 | while ((length = BIO_read(bio, buffer, bufsize)) > 0) 152 | { 153 | /* do nothing */ 154 | } 155 | 156 | BIO_free(bio); 157 | } 158 | else if((bio_err = BIO_new(BIO_s_file())) != NULL) 159 | { 160 | /* HTTP request failed */ 161 | /* 162 | BIO_set_fp_amiga(bio_err, Output(), BIO_NOCLOSE | BIO_FP_TEXT); 163 | ERR_print_errors(bio_err); 164 | */ 165 | 166 | ERR_print_errors_cb(err_cb, 0); 167 | BIO_free(bio_err); 168 | } 169 | 170 | /* Free our custom headers */ 171 | sk_CONF_VALUE_pop_free(headers,(void (*)(CONF_VALUE *))stub_X509V3_conf_free); 172 | 173 | return (bio != NULL); 174 | } 175 | 176 | 177 | long http_get_version(char *buffer, ULONG bufsize) 178 | { 179 | SSL_CTX *SSL_ctx = NULL; 180 | int res = 0; 181 | BOOL result=FALSE; 182 | 183 | SocketBase = OpenLibrary("bsdsocket.library",4); 184 | if (!SocketBase) 185 | { 186 | return(AHTTP_ERR_NOTCPIP); 187 | } 188 | #ifdef __amigaos4__ 189 | else 190 | { 191 | ISocket = (struct SocketIFace *)GetInterface(SocketBase,"main",1,NULL); 192 | } 193 | #endif 194 | 195 | if((AmiSSLMasterBase = OpenLibrary("amisslmaster.library", AMISSLMASTER_MIN_VERSION))!=NULL) { 196 | #ifdef __amigaos4__ 197 | if((IAmiSSLMaster = (struct AmiSSLMasterIFace *)GetInterface((struct Library *)AmiSSLMasterBase, "main", 1, NULL))!=0) { 198 | if(OpenAmiSSLTags(AMISSL_CURRENT_VERSION, 199 | AmiSSL_UsesOpenSSLStructs, TRUE, 200 | AmiSSL_GetIAmiSSL, &IAmiSSL, 201 | AmiSSL_ISocket, ISocket, 202 | // AmiSSL_ErrNoPtr, &errno, 203 | TAG_DONE) == 0) { 204 | #else 205 | if(OpenAmiSSLTags(AMISSL_CURRENT_VERSION, 206 | AmiSSL_UsesOpenSSLStructs, TRUE, 207 | AmiSSL_GetAmiSSLBase, &AmiSSLBase, 208 | AmiSSL_GetAmiSSLExtBase, &AmiSSLExtBase, 209 | AmiSSL_SocketBase, SocketBase, 210 | AmiSSL_ErrNoPtr, &errno, 211 | TAG_DONE) == 0) { 212 | #endif 213 | if((SSL_ctx = SSL_CTX_new(TLS_client_method()))!=NULL) result = TRUE; 214 | } 215 | #ifdef __amigaos4__ 216 | } 217 | #endif 218 | } 219 | 220 | if(result == FALSE) { 221 | return AHTTP_ERR_AMISSL; 222 | } 223 | 224 | res = http_get_url("https://www.unsatisfactorysoftware.co.uk/ver.php?f=avalanche", SSL_ctx, buffer, bufsize); 225 | 226 | SSL_CTX_free(SSL_ctx); 227 | http_closesocketlibs(); 228 | 229 | if(res) { 230 | return AHTTP_ERR_NONE; 231 | } else { 232 | return AHTTP_ERR_UNKNOWN; 233 | } 234 | } 235 | 236 | BOOL http_check_version(void *awin) 237 | { 238 | ULONG bufsize = 10; 239 | char *buffer = AllocVec(bufsize + 1, MEMF_CLEAR); 240 | BOOL update_available = FALSE; 241 | 242 | if(buffer) { 243 | long res = http_get_version(buffer, bufsize); 244 | 245 | if(res == AHTTP_ERR_NONE) { 246 | char *dot = NULL; 247 | 248 | long val = strtol(buffer, &dot, 10); 249 | 250 | if(val > VERSION) { 251 | update_available = TRUE; 252 | } 253 | 254 | if(val == VERSION) { 255 | long rev = strtol(dot + 1, NULL, 10); 256 | 257 | if(rev > REVISION) { 258 | update_available = TRUE; 259 | } 260 | } 261 | 262 | char message[101]; 263 | 264 | if(update_available) { 265 | snprintf(message, 100, locale_get_string(MSG_NEWVERSION), buffer); 266 | } else { 267 | snprintf(message, 100, locale_get_string(MSG_NONEWVERSION)); 268 | } 269 | 270 | open_info_req(message, locale_get_string(MSG_OK), awin); 271 | 272 | } else if(res == AHTTP_ERR_NOTCPIP) { 273 | open_error_req(locale_get_string(MSG_ERR_NOTCPIP), locale_get_string(MSG_OK), awin); 274 | } else if(res == AHTTP_ERR_AMISSL) { 275 | open_error_req(locale_get_string(MSG_ERR_AMISSL), locale_get_string(MSG_OK), awin); 276 | } else { 277 | if(err_txt) { 278 | open_error_req(err_txt, locale_get_string(MSG_OK), awin); 279 | free(err_txt); 280 | } else { 281 | open_error_req(locale_get_string(MSG_ERR_UNKNOWN), locale_get_string(MSG_OK), awin); 282 | } 283 | } 284 | 285 | FreeVec(buffer); 286 | 287 | return TRUE; 288 | } 289 | 290 | return FALSE; 291 | } -------------------------------------------------------------------------------- /src/http.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef AVALANCHE_HTTP_H 16 | #define AVALANCHE_HTTP_H 1 17 | 18 | #include 19 | 20 | BOOL http_check_version(void *awin); 21 | #endif 22 | -------------------------------------------------------------------------------- /src/libs.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | 17 | #include 18 | 19 | #ifndef __amigaos4__ 20 | #include 21 | #include 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include 31 | #include 32 | #include 33 | #include 34 | #else 35 | #include 36 | #endif 37 | 38 | #include 39 | 40 | #include "libs.h" 41 | #include "locale.h" 42 | 43 | #ifdef __amigaos4__ 44 | #define ALIB_OPEN(LIB, LIBVER, PREFIX) \ 45 | if((PREFIX##Base = (struct Library *)OpenLibrary(LIB, LIBVER))) { \ 46 | I##PREFIX = (struct PREFIX##IFace *)GetInterface((struct Library *)PREFIX##Base, "main", 1, NULL); \ 47 | if(I##PREFIX == NULL) { \ 48 | ALIB_CLOSE(PREFIX) \ 49 | printf(locale_get_string(MSG_INTERFACE)); \ 50 | printf(locale_get_string(MSG_UNABLETOOPENLIBRARY), LIB, LIBVER); \ 51 | return FALSE; \ 52 | } \ 53 | } else { \ 54 | printf(locale_get_string(MSG_UNABLETOOPENLIBRARY), LIB, LIBVER); \ 55 | return FALSE; \ 56 | } 57 | 58 | #define ALIB_CLOSE(PREFIX) \ 59 | if(I##PREFIX) DropInterface((struct Interface *)I##PREFIX); \ 60 | if(PREFIX##Base) CloseLibrary((struct Library *)PREFIX##Base); \ 61 | I##PREFIX = NULL; \ 62 | PREFIX##Base = NULL; 63 | 64 | #define ALIB_STRUCT(PREFIX) \ 65 | struct Library *PREFIX##Base = NULL; \ 66 | struct PREFIX##IFace *I##PREFIX = NULL; 67 | 68 | #define CLASS_OPEN(CLASS, CLASSVER, PREFIX, CLASSGET, NEEDINTERFACE) \ 69 | if((PREFIX##Base = OpenClass(CLASS, CLASSVER, &PREFIX##Class))) { \ 70 | if(NEEDINTERFACE == TRUE) { \ 71 | I##PREFIX = (struct PREFIX##IFace *)GetInterface((struct Library *)PREFIX##Base, "main", 1, NULL); \ 72 | if(I##PREFIX == NULL) { \ 73 | printf(locale_get_string(MSG_INTERFACE)); \ 74 | printf(locale_get_string(MSG_UNABLETOOPENLIBRARY), CLASS, CLASSVER); \ 75 | return FALSE; \ 76 | } \ 77 | } \ 78 | } \ 79 | if(PREFIX##Class == NULL) { \ 80 | printf(locale_get_string(MSG_UNABLETOOPENLIBRARY), CLASS, CLASSVER); \ 81 | return FALSE; \ 82 | } 83 | 84 | #define CLASS_CLOSE(PREFIX) \ 85 | if(I##PREFIX) DropInterface((struct Interface *)I##PREFIX); \ 86 | if(PREFIX##Base) CloseClass(PREFIX##Base); \ 87 | I##PREFIX = NULL; \ 88 | PREFIX##Base = NULL; 89 | 90 | #define CLASS_STRUCT(PREFIX) \ 91 | struct ClassLibrary *PREFIX##Base = NULL; \ 92 | struct PREFIX##IFace *I##PREFIX = NULL; \ 93 | Class *PREFIX##Class = NULL; 94 | 95 | #else 96 | 97 | #define ALIB_OPEN(LIB, LIBVER, PREFIX) \ 98 | if((!(PREFIX##Base = (struct PREFIX##Base *)OpenLibrary(LIB, LIBVER)))) { \ 99 | printf(locale_get_string(MSG_UNABLETOOPENLIBRARY), LIB, LIBVER); \ 100 | return FALSE; \ 101 | } 102 | 103 | #define ALIB_CLOSE(PREFIX) \ 104 | if(PREFIX##Base) CloseLibrary((struct Library *)PREFIX##Base); \ 105 | PREFIX##Base = NULL; 106 | 107 | #define ALIB_STRUCT(PREFIX) struct PREFIX##Base *PREFIX##Base = NULL; 108 | 109 | #define CLASS_OPEN(CLASS, CLASSVER, PREFIX, CLASSGET, N) \ 110 | if((PREFIX##Base = OpenLibrary(CLASS, CLASSVER))) { \ 111 | PREFIX##Class = CLASSGET##_GetClass(); \ 112 | } \ 113 | if(PREFIX##Class == NULL) { \ 114 | printf(locale_get_string(MSG_UNABLETOOPENLIBRARY), CLASS, CLASSVER); \ 115 | return FALSE; \ 116 | } 117 | 118 | #define CLASS_CLOSE(PREFIX) \ 119 | if(PREFIX##Base) CloseLibrary(PREFIX##Base); \ 120 | PREFIX##Base = NULL; 121 | 122 | #define CLASS_STRUCT(PREFIX) \ 123 | struct Library *PREFIX##Base = NULL; \ 124 | Class *PREFIX##Class = NULL; 125 | 126 | #endif 127 | 128 | ALIB_STRUCT(Asl) 129 | #ifdef __amigaos4__ 130 | ALIB_STRUCT(Commodities) 131 | ALIB_STRUCT(Graphics) 132 | #else 133 | ALIB_STRUCT(Cx) 134 | ALIB_STRUCT(Gfx) 135 | #endif 136 | 137 | ALIB_STRUCT(Icon) 138 | ALIB_STRUCT(Intuition) 139 | //ALIB_STRUCT(Locale) 140 | 141 | #ifndef __amigaos4__ 142 | ALIB_STRUCT(Utility) 143 | #endif 144 | 145 | ALIB_STRUCT(Workbench) 146 | 147 | ALIB_STRUCT(xfdMaster) 148 | ALIB_STRUCT(xvs) 149 | 150 | #ifdef __amigaos4__ 151 | ALIB_STRUCT(XadMaster) 152 | #else 153 | ALIB_STRUCT(xadMaster) 154 | #endif 155 | 156 | #ifdef __amigaos4__ 157 | ALIB_STRUCT(Zip) 158 | #endif 159 | 160 | CLASS_STRUCT(ARexx) 161 | CLASS_STRUCT(BitMap) 162 | CLASS_STRUCT(Button) 163 | CLASS_STRUCT(CheckBox) 164 | CLASS_STRUCT(Chooser) 165 | CLASS_STRUCT(FuelGauge) 166 | CLASS_STRUCT(GetFile) 167 | CLASS_STRUCT(Glyph) 168 | CLASS_STRUCT(Label) 169 | CLASS_STRUCT(Layout) 170 | CLASS_STRUCT(ListBrowser) 171 | CLASS_STRUCT(Requester) 172 | CLASS_STRUCT(String) 173 | CLASS_STRUCT(Window) 174 | 175 | BOOL libs_xvs_init(void) 176 | { 177 | if(xvsBase == NULL) { 178 | ALIB_OPEN("xvs.library", 33, xvs); 179 | } 180 | 181 | return TRUE; 182 | } 183 | 184 | static void libs_xvs_exit(void) 185 | { 186 | if(xvsBase != NULL) { 187 | ALIB_CLOSE(xvs); 188 | } 189 | } 190 | 191 | BOOL libs_zip_init(void) 192 | { 193 | #ifdef __amigaos4__ 194 | if(ZipBase == NULL) { 195 | ALIB_OPEN("zip.library", 54, Zip) 196 | } 197 | 198 | return TRUE; 199 | #else 200 | return FALSE; 201 | #endif 202 | 203 | } 204 | 205 | void libs_zip_exit(void) 206 | { 207 | #ifdef __amigaos4__ 208 | if(ZipBase != NULL) { 209 | ALIB_CLOSE(Zip); 210 | } 211 | #endif 212 | } 213 | 214 | 215 | BOOL libs_open(void) 216 | { 217 | ALIB_OPEN("asl.library", 36, Asl) 218 | #ifdef __amigaos4__ 219 | ALIB_OPEN("commodities.library", 37, Commodities) 220 | ALIB_OPEN("graphics.library", 39, Graphics) 221 | #else 222 | ALIB_OPEN("commodities.library", 37, Cx) 223 | ALIB_OPEN("graphics.library", 39, Gfx) 224 | #endif 225 | ALIB_OPEN("icon.library", 44, Icon) 226 | ALIB_OPEN("intuition.library", 40, Intuition) 227 | // ALIB_OPEN("locale.library", 38, Locale) 228 | ALIB_OPEN("utility.library", 36, Utility) 229 | ALIB_OPEN("workbench.library", 40, Workbench) 230 | 231 | CLASS_OPEN("images/bitmap.image", 41, BitMap, BITMAP, FALSE) 232 | CLASS_OPEN("gadgets/button.gadget", 41, Button, BUTTON, FALSE) 233 | CLASS_OPEN("gadgets/checkbox.gadget", 41, CheckBox, CHECKBOX, FALSE) 234 | CLASS_OPEN("gadgets/chooser.gadget", 45, Chooser, CHOOSER, TRUE) 235 | CLASS_OPEN("gadgets/fuelgauge.gadget", 41, FuelGauge, FUELGAUGE, FALSE) 236 | CLASS_OPEN("gadgets/getfile.gadget", 41, GetFile, GETFILE, FALSE) 237 | CLASS_OPEN("images/glyph.image", 41, Glyph, GLYPH, FALSE) 238 | CLASS_OPEN("images/label.image", 41, Label, LABEL, FALSE) 239 | CLASS_OPEN("gadgets/layout.gadget", 41, Layout, LAYOUT, TRUE) 240 | CLASS_OPEN("gadgets/listbrowser.gadget", 45, ListBrowser, LISTBROWSER, TRUE) 241 | CLASS_OPEN("requester.class", 41, Requester, REQUESTER, FALSE) 242 | CLASS_OPEN("gadgets/string.gadget", 41, String, STRING, FALSE) 243 | CLASS_OPEN("window.class", 47, Window, WINDOW, FALSE) 244 | CLASS_OPEN("arexx.class", 41, ARexx, AREXX, FALSE) 245 | 246 | return TRUE; 247 | } 248 | 249 | void libs_close(void) 250 | { 251 | libs_xvs_exit(); 252 | libs_zip_exit(); 253 | 254 | CLASS_CLOSE(BitMap) 255 | CLASS_CLOSE(Button) 256 | CLASS_CLOSE(CheckBox) 257 | CLASS_CLOSE(Chooser) 258 | CLASS_CLOSE(FuelGauge) 259 | CLASS_CLOSE(GetFile) 260 | CLASS_CLOSE(Glyph) 261 | CLASS_CLOSE(Label) 262 | CLASS_CLOSE(Layout) 263 | CLASS_CLOSE(ListBrowser) 264 | CLASS_CLOSE(Requester) 265 | CLASS_CLOSE(String) 266 | CLASS_CLOSE(Window) 267 | CLASS_CLOSE(ARexx) 268 | 269 | ALIB_CLOSE(Asl) 270 | #ifdef __amigaos4__ 271 | ALIB_CLOSE(Commodities) 272 | ALIB_CLOSE(Graphics) 273 | #else 274 | ALIB_CLOSE(Cx) 275 | ALIB_CLOSE(Gfx) 276 | #endif 277 | ALIB_CLOSE(Icon) 278 | ALIB_CLOSE(Intuition) 279 | // ALIB_CLOSE(Locale) 280 | ALIB_CLOSE(Workbench) 281 | } 282 | 283 | BOOL libs_xad_init(void) 284 | { 285 | #ifdef __amigaos4__ 286 | if(XadMasterBase == NULL) { 287 | ALIB_OPEN("xadmaster.library", 13, XadMaster); 288 | } 289 | #else 290 | if(xadMasterBase == NULL) { 291 | ALIB_OPEN("xadmaster.library", 12, xadMaster); 292 | } 293 | #endif 294 | 295 | return TRUE; 296 | } 297 | 298 | void libs_xad_exit(void) 299 | { 300 | #ifdef __amigaos4__ 301 | if(XadMasterBase != NULL) { 302 | ALIB_CLOSE(XadMaster); 303 | } 304 | #else 305 | if(xadMasterBase != NULL) { 306 | ALIB_CLOSE(xadMaster); 307 | } 308 | #endif 309 | } 310 | 311 | BOOL libs_xfd_init(void) 312 | { 313 | if(xfdMasterBase == NULL) { 314 | ALIB_OPEN("xfdmaster.library", 36, xfdMaster); 315 | } 316 | 317 | return TRUE; 318 | } 319 | 320 | void libs_xfd_exit(void) 321 | { 322 | if(xfdMasterBase != NULL) { 323 | ALIB_CLOSE(xfdMaster); 324 | } 325 | } 326 | -------------------------------------------------------------------------------- /src/libs.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef LIBS_H 16 | #define LIBS_H 1 17 | 18 | #include 19 | 20 | #ifdef __amigaos4__ 21 | #define DeleteFile Delete 22 | #endif 23 | 24 | extern Class *ARexxClass; 25 | extern Class *BitMapClass; 26 | extern Class *ButtonClass; 27 | extern Class *CheckBoxClass; 28 | extern Class *ChooserClass; 29 | extern Class *FuelGaugeClass; 30 | extern Class *GetFileClass; 31 | extern Class *GlyphClass; 32 | extern Class *LabelClass; 33 | extern Class *LayoutClass; 34 | extern Class *ListBrowserClass; 35 | extern Class *RequesterClass; 36 | extern Class *StringClass; 37 | extern Class *WindowClass; 38 | 39 | #define ARexxObj NewObject(ARexxClass, NULL 40 | #define BitMapObj NewObject(BitMapClass, NULL 41 | #define ButtonObj NewObject(ButtonClass, NULL 42 | #define CheckBoxObj NewObject(CheckBoxClass, NULL 43 | #define ChooserObj NewObject(ChooserClass, NULL 44 | #define FuelGaugeObj NewObject(FuelGaugeClass, NULL 45 | #define GetFileObj NewObject(GetFileClass, NULL 46 | #define GlyphObj NewObject(GlyphClass, NULL 47 | #define LabelObj NewObject(LabelClass, NULL 48 | #define LayoutHObj NewObject(LayoutClass, NULL, LAYOUT_Orientation, LAYOUT_ORIENT_HORIZ 49 | #define LayoutVObj NewObject(LayoutClass, NULL, LAYOUT_Orientation, LAYOUT_ORIENT_VERT 50 | #define ListBrowserObj NewObject(ListBrowserClass, NULL 51 | #define RequesterObj NewObject(RequesterClass, NULL 52 | #define StringObj NewObject(StringClass, NULL 53 | #define WindowObj NewObject(WindowClass, NULL 54 | 55 | BOOL libs_open(void); 56 | void libs_close(void); 57 | 58 | BOOL libs_xad_init(void); 59 | void libs_xad_exit(void); 60 | 61 | BOOL libs_xfd_init(void); 62 | void libs_xfd_exit(void); 63 | 64 | BOOL libs_xvs_init(void); 65 | 66 | BOOL libs_zip_init(void); 67 | void libs_zip_exit(void); 68 | 69 | #endif 70 | -------------------------------------------------------------------------------- /src/locale.c: -------------------------------------------------------------------------------- 1 | 2 | /* 3 | ** locale.c 4 | ** 5 | ** (c) 2011 by Guido Mersmann 6 | ** 7 | ** Object source created by SimpleCat. 8 | ** 9 | ** DO NOT EDIT THIS FILE UNLESS YOU KNOW WHAT YOU ARE DOING 10 | ** 11 | ** Usage is quite simple. 12 | ** 13 | ** 1. Add this file to object creation list in makefile. 14 | ** 15 | ** 2. Call Locale_Open() and Locale_Close() on startup and shut down of your code. 16 | ** There is no need to check any result. 17 | ** 18 | ** 3. Make sure the marked include line within 'locale.h' header file uses 19 | ** the name of your string header file. Thats name in .CS file which is set with 20 | ** TARGET C header file command or when using the GUI in target list. By default 21 | ** its "locale_strings.h". Make sure you use the following switches for the C 22 | ** target to create a valid header file for this code: 23 | ** NoCode NoArray NoBlockStatic 24 | ** 25 | ** 4. Include the 'locale.h' header everywhere you need a locale string. 26 | ** 27 | ** 5. Call locale_get_string( id ) where ever you need a locale string. "id" is the label name 28 | ** you address the strings. To follow the style guide you should name the files 29 | ** using "MSG_" prefix. 30 | ** 31 | ** 6. Thats all! 32 | ** 33 | */ 34 | 35 | #include 36 | #include 37 | 38 | #include 39 | #include 40 | 41 | #define CATCOMP_BLOCK 1 /* enable CATCOMP_BLOCK */ 42 | #include "locale.h" /* prototypes and catcomp block */ 43 | 44 | /*************************************************************************/ 45 | 46 | #ifdef __amigaos4__ 47 | struct Library *LocaleBase; 48 | struct LocaleIFace *ILocale; 49 | #else 50 | struct LocaleBase *LocaleBase; 51 | #endif 52 | 53 | static struct Locale *locale_locale; 54 | static struct Catalog *locale_catalog; 55 | 56 | /*************************************************************************/ 57 | 58 | /* /// Locale_Open */ 59 | 60 | /*************************************************************************/ 61 | 62 | BOOL Locale_Open( STRPTR catname, ULONG version, ULONG revision) 63 | { 64 | if( (LocaleBase = (APTR) OpenLibrary( "locale.library",0 )) ) { 65 | #ifdef __amigaos4__ 66 | if( (ILocale = (struct LocaleIFace *) GetInterface( LocaleBase, "main", 1, NULL)) ) { 67 | #endif 68 | if( (locale_locale = OpenLocale(NULL)) ) { 69 | if( (locale_catalog = OpenCatalogA(locale_locale, catname, TAG_DONE)) ) { 70 | return(TRUE); 71 | } 72 | CloseLocale(locale_locale); 73 | locale_locale = NULL; 74 | } 75 | #ifdef __amigaos4__ 76 | DropInterface((struct Interface *)ILocale); 77 | } 78 | #endif 79 | CloseLibrary( (APTR) LocaleBase ); 80 | LocaleBase = NULL; 81 | } 82 | return(FALSE); 83 | } 84 | /* \\\ Locale_Open */ 85 | 86 | /* /// Locale_Close */ 87 | 88 | /*************************************************************************/ 89 | 90 | void Locale_Close(void) 91 | { 92 | if( LocaleBase) { 93 | if( locale_catalog) { 94 | CloseCatalog(locale_catalog); 95 | locale_catalog = NULL; 96 | } 97 | if( locale_locale) { 98 | CloseLocale(locale_locale); 99 | locale_locale = NULL; 100 | } 101 | #ifdef __amigaos4__ 102 | DropInterface((struct Interface *)ILocale); 103 | #endif 104 | CloseLibrary( (APTR) LocaleBase ); 105 | LocaleBase = NULL; 106 | } 107 | } 108 | /* \\\ */ 109 | 110 | /* /// locale_get_string */ 111 | 112 | /*************************************************************************/ 113 | 114 | STRPTR locale_get_string(long id) 115 | { 116 | LONG *l; 117 | STRPTR builtin; 118 | 119 | l = (LONG *)CatCompBlock; 120 | 121 | while (*l != id ) { 122 | UWORD *w = (UWORD *)((ULONG)l + 4); 123 | l = (LONG *)((ULONG)l + (ULONG)*w + 6); 124 | } 125 | builtin = (STRPTR)((ULONG)l + 6); 126 | 127 | if ( locale_catalog && LocaleBase ) { 128 | return( (APTR) GetCatalogStr( locale_catalog, id, builtin)); 129 | } 130 | return(builtin); 131 | } 132 | /* \\\ locale_get_string */ 133 | 134 | struct Locale *locale_get_locale(void) 135 | { 136 | return locale_locale; 137 | } 138 | -------------------------------------------------------------------------------- /src/locale.h: -------------------------------------------------------------------------------- 1 | #ifndef LOCALE_H 2 | #define LOCALE_H 1 3 | 4 | #define CATCOMP_NUMBERS 5 | 6 | /* 7 | ** locale.h 8 | ** 9 | ** (c) 2006 by Guido Mersmann 10 | ** 11 | ** Object source created by SimpleCat 12 | */ 13 | 14 | /*************************************************************************/ 15 | 16 | #include "locale_strings.h" /* change name to correct locale header if needed */ 17 | 18 | /* 19 | ** Prototypes 20 | */ 21 | 22 | BOOL Locale_Open( STRPTR catname, ULONG version, ULONG revision); 23 | void Locale_Close(void); 24 | STRPTR locale_get_string(long ID); 25 | struct Locale *locale_get_locale(void); 26 | 27 | /*************************************************************************/ 28 | 29 | #endif /* LOCALE_H */ 30 | -------------------------------------------------------------------------------- /src/locale_strings.h: -------------------------------------------------------------------------------- 1 | #ifndef LOCALE_STRINGS_H_H 2 | #define LOCALE_STRINGS_H_H 3 | 4 | 5 | /****************************************************************************/ 6 | 7 | 8 | /* This file was created automatically by CatComp. 9 | * Do NOT edit by hand! 10 | */ 11 | 12 | 13 | #ifndef EXEC_TYPES_H 14 | #include 15 | #endif 16 | 17 | #ifdef CATCOMP_CODE 18 | #ifndef CATCOMP_BLOCK 19 | #define CATCOMP_ARRAY 20 | #endif 21 | #endif 22 | 23 | #ifdef CATCOMP_ARRAY 24 | #ifndef CATCOMP_NUMBERS 25 | #define CATCOMP_NUMBERS 26 | #endif 27 | #ifndef CATCOMP_STRINGS 28 | #define CATCOMP_STRINGS 29 | #endif 30 | #endif 31 | 32 | #ifdef CATCOMP_BLOCK 33 | #ifndef CATCOMP_STRINGS 34 | #define CATCOMP_STRINGS 35 | #endif 36 | #endif 37 | 38 | 39 | /****************************************************************************/ 40 | 41 | 42 | #ifdef CATCOMP_NUMBERS 43 | 44 | #define MSG_EXTRACT 0 45 | #define MSG_SAVE 1 46 | #define MSG_USE 2 47 | #define MSG_CANCEL 3 48 | #define MSG_PREFERENCES 4 49 | #define MSG_PROJECT 5 50 | #define MSG_OPEN 6 51 | #define MSG_ARCHIVEINFO 7 52 | #define MSG_ABOUT 8 53 | #define MSG_QUIT 9 54 | #define MSG_EDIT 10 55 | #define MSG_SELECTALL 11 56 | #define MSG_CLEARSELECTION 12 57 | #define MSG_INVERTSELECTION 13 58 | #define MSG_SETTINGS 14 59 | #define MSG_SCANFORVIRUSES 15 60 | #define MSG_HIERARCHICALBROWSEREXPERIMENTAL 16 61 | #define MSG_SAVEWINDOWPOSITION 17 62 | #define MSG_CONFIRMQUIT 18 63 | #define MSG_SAVESETTINGS 19 64 | #define MSG_STOP 20 65 | #define MSG_NAME 21 66 | #define MSG_SIZE 22 67 | #define MSG_DATE 23 68 | #define MSG_SELECTARCHIVE 24 69 | #define MSG_ARCHIVE 25 70 | #define MSG_SELECTDESTINATION 26 71 | #define MSG_DESTINATION 27 72 | #define MSG_ALREADYEXISTSOVERWRITE 28 73 | #define MSG_FILEARCHIVE 29 74 | #define MSG_DISKARCHIVE 30 75 | #define MSG_DISKIMAGE 31 76 | #define MSG_UNKNOWN 32 77 | #define MSG_OK 33 78 | #define MSG_CRUNCHED 34 79 | #define MSG_ERRORDECRUNCHING 35 80 | #define MSG_VIRUSSCANNINGWILLBEDISABLED 36 81 | #define MSG_XVSLIBRARYFAILEDSELFTEST 37 82 | #define MSG_OUTOFMEMORYSCANNINGFILE 38 83 | #define MSG_FILEHASBEENDELETED 39 84 | #define MSG_FILECOULDNOTBEDELETED 40 85 | #define MSG_VIRUSFOUNDETECTIONNAME 41 86 | #define MSG_GPL 42 87 | #define MSG_UNABLETOOPENREQUESTERTOSHOWERRORS 43 88 | #define MSG_UNABLETOOPENLIBRARY 44 89 | #define MSG_AREYOUSUREYOUWANTTOEXIT 45 90 | #define MSG_YESNO 46 91 | #define MSG_YESYESTOALLNONOTOALLABORT 47 92 | #define MSG_ARCHIVEISENCRYPTEDPLEASEENTERPASSWORD 48 93 | #define MSG_OKCANCEL 49 94 | #define MSG_UNABLETOOPENREQUESTERTOASKPASSWORD 50 95 | #define MSG_INTERFACE 51 96 | #define MSG_IGNOREFILESYSTEMS 52 97 | #define MSG_CXDESCRIPTION 53 98 | #define MSG_APPMENU_EXTRACTHERE 54 99 | #define MSG_SNAPSHOT 55 100 | #define MSG_UNABLETOOPENFILE 56 101 | #define MSG_OUTOFMEMORY 57 102 | #define MSG_LASTWINDOWCLOSED 58 103 | #define MSG_QUITHIDECANCEL 59 104 | #define MSG_NEWWINDOW 60 105 | #define MSG_QUITCFG_ASK 61 106 | #define MSG_QUITCFG_QUIT 62 107 | #define MSG_QUITCFG_HIDE 63 108 | #define MSG_LASTWINDOWACTION 64 109 | #define MSG_ADDFILES 65 110 | #define MSG_DELFILES 66 111 | #define MSG_UNABLETOOPENZIP 67 112 | #define MSG_LHAERROR 68 113 | #define MSG_SKIPRETRYABORT 69 114 | #define MSG_ARCHIVEMUSTHAVEENTRIES 70 115 | #define MSG_CONFIRMDELETE 71 116 | #define MSG_VIEWMODEBROWSER 72 117 | #define MSG_VIEWMODELIST 73 118 | #define MSG_VIEWMODE 74 119 | #define MSG_ERR_TREE_ALLOC 75 120 | #define MSG_NEWARCHIVE 76 121 | #define MSG_TYPE 77 122 | #define MSG_CREATE 78 123 | #define MSG_DIR 79 124 | #define MSG_PARENT 80 125 | #define MSG_PACKEDSIZE 81 126 | #define MSG_SNAPSHOT_WARNING 82 127 | #define MSG_ERR_NOTCPIP 83 128 | #define MSG_ERR_AMISSL 84 129 | #define MSG_ERR_UNKNOWN 85 130 | #define MSG_NEWVERSION 86 131 | #define MSG_NONEWVERSION 87 132 | #define MSG_CHECKVERSION 88 133 | 134 | #endif /* CATCOMP_NUMBERS */ 135 | 136 | 137 | /****************************************************************************/ 138 | 139 | 140 | #ifdef CATCOMP_STRINGS 141 | 142 | #define MSG_EXTRACT_STR "E_xtract" 143 | #define MSG_SAVE_STR "Save" 144 | #define MSG_USE_STR "Use" 145 | #define MSG_CANCEL_STR "Cancel" 146 | #define MSG_PREFERENCES_STR "Preferences..." 147 | #define MSG_PROJECT_STR "Project" 148 | #define MSG_OPEN_STR "Open..." 149 | #define MSG_ARCHIVEINFO_STR "Archive info..." 150 | #define MSG_ABOUT_STR "About..." 151 | #define MSG_QUIT_STR "Quit..." 152 | #define MSG_EDIT_STR "Edit" 153 | #define MSG_SELECTALL_STR "Select all" 154 | #define MSG_CLEARSELECTION_STR "Clear selection" 155 | #define MSG_INVERTSELECTION_STR "Invert selection" 156 | #define MSG_SETTINGS_STR "Settings" 157 | #define MSG_SCANFORVIRUSES_STR "Scan for viruses" 158 | #define MSG_HIERARCHICALBROWSEREXPERIMENTAL_STR "Hierarchical browser (experimental)" 159 | #define MSG_SAVEWINDOWPOSITION_STR "Save window position" 160 | #define MSG_CONFIRMQUIT_STR "Confirm quit" 161 | #define MSG_SAVESETTINGS_STR "Save settings" 162 | #define MSG_STOP_STR "_Stop" 163 | #define MSG_NAME_STR "Name" 164 | #define MSG_SIZE_STR "Size" 165 | #define MSG_DATE_STR "Date" 166 | #define MSG_SELECTARCHIVE_STR "Select Archive" 167 | #define MSG_ARCHIVE_STR "_Archive" 168 | #define MSG_SELECTDESTINATION_STR "Select Destination" 169 | #define MSG_DESTINATION_STR "_Destination" 170 | #define MSG_ALREADYEXISTSOVERWRITE_STR "%s already exists, overwrite?" 171 | #define MSG_FILEARCHIVE_STR "file archive" 172 | #define MSG_DISKARCHIVE_STR "disk archive" 173 | #define MSG_DISKIMAGE_STR "disk image" 174 | #define MSG_UNKNOWN_STR "unknown" 175 | #define MSG_OK_STR "_OK" 176 | #define MSG_CRUNCHED_STR "%s crunched" 177 | #define MSG_ERRORDECRUNCHING_STR "Error decrunching" 178 | #define MSG_VIRUSSCANNINGWILLBEDISABLED_STR "Virus scanning will be disabled.\n" 179 | #define MSG_XVSLIBRARYFAILEDSELFTEST_STR "xvs.library failed self-test," 180 | #define MSG_OUTOFMEMORYSCANNINGFILE_STR "Out of memory scanning file:\n%s" 181 | #define MSG_FILEHASBEENDELETED_STR "File has been deleted." 182 | #define MSG_FILECOULDNOTBEDELETED_STR "File could not be deleted." 183 | #define MSG_VIRUSFOUNDETECTIONNAME_STR "Virus found in %s\nDetection name: %s\n\n" 184 | #define MSG_GPL_STR "This program is free software; you can redistribute it and/or modify\nit under the terms of the GNU General Public License as published by\nthe Free Software Foundation; either version 2 of the License, or\n(at your option) any later version.\n\nThis program is distributed in the hope that it will be useful,\nbut WITHOUT ANY WARRANTY; without even the implied warranty of\nMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\nGNU General Public License for more details." 185 | #define MSG_UNABLETOOPENREQUESTERTOSHOWERRORS_STR "Unable to open requester to show error;\n%s [%s]\n" 186 | #define MSG_UNABLETOOPENLIBRARY_STR "Unable to open %s v%d\n" 187 | #define MSG_AREYOUSUREYOUWANTTOEXIT_STR "Are you sure you want to exit?" 188 | #define MSG_YESNO_STR "_Yes|_No" 189 | #define MSG_YESYESTOALLNONOTOALLABORT_STR "_Yes|Yes to _all|_No|N_o to all|Abort" 190 | #define MSG_ARCHIVEISENCRYPTEDPLEASEENTERPASSWORD_STR "Archive is encrypted, please enter password." 191 | #define MSG_OKCANCEL_STR "_OK|_Cancel" 192 | #define MSG_UNABLETOOPENREQUESTERTOASKPASSWORD_STR "Unable to open requester to ask password\n" 193 | #define MSG_INTERFACE_STR "(interface)" 194 | #define MSG_IGNOREFILESYSTEMS_STR "Ignore filesystems" 195 | #define MSG_CXDESCRIPTION_STR "Unarchive GUI for XAD/XFD" 196 | #define MSG_APPMENU_EXTRACTHERE_STR "Extract here" 197 | #define MSG_SNAPSHOT_STR "Snapshot window" 198 | #define MSG_UNABLETOOPENFILE_STR "Unable to open file" 199 | #define MSG_OUTOFMEMORY_STR "Not enough memory" 200 | #define MSG_LASTWINDOWCLOSED_STR "Last window closed." 201 | #define MSG_QUITHIDECANCEL_STR "Quit|Hide|Cancel" 202 | #define MSG_NEWWINDOW_STR "New window..." 203 | #define MSG_QUITCFG_ASK_STR "Ask" 204 | #define MSG_QUITCFG_QUIT_STR "Quit" 205 | #define MSG_QUITCFG_HIDE_STR "Hide" 206 | #define MSG_LASTWINDOWACTION_STR "When last window closed:" 207 | #define MSG_ADDFILES_STR "Add files..." 208 | #define MSG_DELFILES_STR "Delete selected items..." 209 | #define MSG_UNABLETOOPENZIP_STR "Unable to open Zip for writing" 210 | #define MSG_LHAERROR_STR "Error processing file: %s" 211 | #define MSG_SKIPRETRYABORT_STR "Skip|Retry|Abort" 212 | #define MSG_ARCHIVEMUSTHAVEENTRIES_STR "Archive must contain at least one file." 213 | #define MSG_CONFIRMDELETE_STR "Are you sure you want to delete the selected entries?" 214 | #define MSG_VIEWMODEBROWSER_STR "Browser" 215 | #define MSG_VIEWMODELIST_STR "List" 216 | #define MSG_VIEWMODE_STR "View mode" 217 | #define MSG_ERR_TREE_ALLOC_STR "Tree entries exceed allocated memory" 218 | #define MSG_NEWARCHIVE_STR "New archive..." 219 | #define MSG_TYPE_STR "_Type" 220 | #define MSG_CREATE_STR "_Create" 221 | #define MSG_DIR_STR "(dir)" 222 | #define MSG_PARENT_STR "(parent)" 223 | #define MSG_PACKEDSIZE_STR "Packed Size" 224 | #define MSG_SNAPSHOT_WARNING_STR "This will not be persistent until prefs are saved!" 225 | #define MSG_ERR_NOTCPIP_STR "Please start your TCP/IP stack" 226 | #define MSG_ERR_AMISSL_STR "Unable to open AmiSSL v5" 227 | #define MSG_ERR_UNKNOWN_STR "Unknown error" 228 | #define MSG_NEWVERSION_STR "New version (%s) available" 229 | #define MSG_NONEWVERSION_STR "Current version is up-to-date" 230 | #define MSG_CHECKVERSION_STR "Check for update..." 231 | 232 | #endif /* CATCOMP_STRINGS */ 233 | 234 | 235 | /****************************************************************************/ 236 | 237 | 238 | #ifdef CATCOMP_BLOCK 239 | 240 | STATIC CONST UBYTE CatCompBlock[] = 241 | { 242 | "\x00\x00\x00\x00\x00\x0A" 243 | MSG_EXTRACT_STR "\x00\x00" 244 | "\x00\x00\x00\x01\x00\x06" 245 | MSG_SAVE_STR "\x00\x00" 246 | "\x00\x00\x00\x02\x00\x04" 247 | MSG_USE_STR "\x00" 248 | "\x00\x00\x00\x03\x00\x08" 249 | MSG_CANCEL_STR "\x00\x00" 250 | "\x00\x00\x00\x04\x00\x10" 251 | MSG_PREFERENCES_STR "\x00\x00" 252 | "\x00\x00\x00\x05\x00\x08" 253 | MSG_PROJECT_STR "\x00" 254 | "\x00\x00\x00\x06\x00\x08" 255 | MSG_OPEN_STR "\x00" 256 | "\x00\x00\x00\x07\x00\x10" 257 | MSG_ARCHIVEINFO_STR "\x00" 258 | "\x00\x00\x00\x08\x00\x0A" 259 | MSG_ABOUT_STR "\x00\x00" 260 | "\x00\x00\x00\x09\x00\x08" 261 | MSG_QUIT_STR "\x00" 262 | "\x00\x00\x00\x0A\x00\x06" 263 | MSG_EDIT_STR "\x00\x00" 264 | "\x00\x00\x00\x0B\x00\x0C" 265 | MSG_SELECTALL_STR "\x00\x00" 266 | "\x00\x00\x00\x0C\x00\x10" 267 | MSG_CLEARSELECTION_STR "\x00" 268 | "\x00\x00\x00\x0D\x00\x12" 269 | MSG_INVERTSELECTION_STR "\x00\x00" 270 | "\x00\x00\x00\x0E\x00\x0A" 271 | MSG_SETTINGS_STR "\x00\x00" 272 | "\x00\x00\x00\x0F\x00\x12" 273 | MSG_SCANFORVIRUSES_STR "\x00\x00" 274 | "\x00\x00\x00\x10\x00\x24" 275 | MSG_HIERARCHICALBROWSEREXPERIMENTAL_STR "\x00" 276 | "\x00\x00\x00\x11\x00\x16" 277 | MSG_SAVEWINDOWPOSITION_STR "\x00\x00" 278 | "\x00\x00\x00\x12\x00\x0E" 279 | MSG_CONFIRMQUIT_STR "\x00\x00" 280 | "\x00\x00\x00\x13\x00\x0E" 281 | MSG_SAVESETTINGS_STR "\x00" 282 | "\x00\x00\x00\x14\x00\x06" 283 | MSG_STOP_STR "\x00" 284 | "\x00\x00\x00\x15\x00\x06" 285 | MSG_NAME_STR "\x00\x00" 286 | "\x00\x00\x00\x16\x00\x06" 287 | MSG_SIZE_STR "\x00\x00" 288 | "\x00\x00\x00\x17\x00\x06" 289 | MSG_DATE_STR "\x00\x00" 290 | "\x00\x00\x00\x18\x00\x10" 291 | MSG_SELECTARCHIVE_STR "\x00\x00" 292 | "\x00\x00\x00\x19\x00\x0A" 293 | MSG_ARCHIVE_STR "\x00\x00" 294 | "\x00\x00\x00\x1A\x00\x14" 295 | MSG_SELECTDESTINATION_STR "\x00\x00" 296 | "\x00\x00\x00\x1B\x00\x0E" 297 | MSG_DESTINATION_STR "\x00\x00" 298 | "\x00\x00\x00\x1C\x00\x1E" 299 | MSG_ALREADYEXISTSOVERWRITE_STR "\x00" 300 | "\x00\x00\x00\x1D\x00\x0E" 301 | MSG_FILEARCHIVE_STR "\x00\x00" 302 | "\x00\x00\x00\x1E\x00\x0E" 303 | MSG_DISKARCHIVE_STR "\x00\x00" 304 | "\x00\x00\x00\x1F\x00\x0C" 305 | MSG_DISKIMAGE_STR "\x00\x00" 306 | "\x00\x00\x00\x20\x00\x08" 307 | MSG_UNKNOWN_STR "\x00" 308 | "\x00\x00\x00\x21\x00\x04" 309 | MSG_OK_STR "\x00" 310 | "\x00\x00\x00\x22\x00\x0C" 311 | MSG_CRUNCHED_STR "\x00" 312 | "\x00\x00\x00\x23\x00\x12" 313 | MSG_ERRORDECRUNCHING_STR "\x00" 314 | "\x00\x00\x00\x24\x00\x22" 315 | MSG_VIRUSSCANNINGWILLBEDISABLED_STR "\x00" 316 | "\x00\x00\x00\x25\x00\x1E" 317 | MSG_XVSLIBRARYFAILEDSELFTEST_STR "\x00" 318 | "\x00\x00\x00\x26\x00\x20" 319 | MSG_OUTOFMEMORYSCANNINGFILE_STR "\x00" 320 | "\x00\x00\x00\x27\x00\x18" 321 | MSG_FILEHASBEENDELETED_STR "\x00\x00" 322 | "\x00\x00\x00\x28\x00\x1C" 323 | MSG_FILECOULDNOTBEDELETED_STR "\x00\x00" 324 | "\x00\x00\x00\x29\x00\x28" 325 | MSG_VIRUSFOUNDETECTIONNAME_STR "\x00\x00" 326 | "\x00\x00\x00\x2A\x01\xDC" 327 | MSG_GPL_STR "\x00\x00" 328 | "\x00\x00\x00\x2B\x00\x32" 329 | MSG_UNABLETOOPENREQUESTERTOSHOWERRORS_STR "\x00\x00" 330 | "\x00\x00\x00\x2C\x00\x18" 331 | MSG_UNABLETOOPENLIBRARY_STR "\x00\x00" 332 | "\x00\x00\x00\x2D\x00\x20" 333 | MSG_AREYOUSUREYOUWANTTOEXIT_STR "\x00\x00" 334 | "\x00\x00\x00\x2E\x00\x0A" 335 | MSG_YESNO_STR "\x00\x00" 336 | "\x00\x00\x00\x2F\x00\x26" 337 | MSG_YESYESTOALLNONOTOALLABORT_STR "\x00" 338 | "\x00\x00\x00\x30\x00\x2E" 339 | MSG_ARCHIVEISENCRYPTEDPLEASEENTERPASSWORD_STR "\x00\x00" 340 | "\x00\x00\x00\x31\x00\x0C" 341 | MSG_OKCANCEL_STR "\x00" 342 | "\x00\x00\x00\x32\x00\x2A" 343 | MSG_UNABLETOOPENREQUESTERTOASKPASSWORD_STR "\x00" 344 | "\x00\x00\x00\x33\x00\x0C" 345 | MSG_INTERFACE_STR "\x00" 346 | "\x00\x00\x00\x34\x00\x14" 347 | MSG_IGNOREFILESYSTEMS_STR "\x00\x00" 348 | "\x00\x00\x00\x35\x00\x1A" 349 | MSG_CXDESCRIPTION_STR "\x00" 350 | "\x00\x00\x00\x36\x00\x0E" 351 | MSG_APPMENU_EXTRACTHERE_STR "\x00\x00" 352 | "\x00\x00\x00\x37\x00\x10" 353 | MSG_SNAPSHOT_STR "\x00" 354 | "\x00\x00\x00\x38\x00\x14" 355 | MSG_UNABLETOOPENFILE_STR "\x00" 356 | "\x00\x00\x00\x39\x00\x12" 357 | MSG_OUTOFMEMORY_STR "\x00" 358 | "\x00\x00\x00\x3A\x00\x14" 359 | MSG_LASTWINDOWCLOSED_STR "\x00" 360 | "\x00\x00\x00\x3B\x00\x12" 361 | MSG_QUITHIDECANCEL_STR "\x00\x00" 362 | "\x00\x00\x00\x3C\x00\x0E" 363 | MSG_NEWWINDOW_STR "\x00" 364 | "\x00\x00\x00\x3D\x00\x04" 365 | MSG_QUITCFG_ASK_STR "\x00" 366 | "\x00\x00\x00\x3E\x00\x06" 367 | MSG_QUITCFG_QUIT_STR "\x00\x00" 368 | "\x00\x00\x00\x3F\x00\x06" 369 | MSG_QUITCFG_HIDE_STR "\x00\x00" 370 | "\x00\x00\x00\x40\x00\x1A" 371 | MSG_LASTWINDOWACTION_STR "\x00\x00" 372 | "\x00\x00\x00\x41\x00\x0E" 373 | MSG_ADDFILES_STR "\x00\x00" 374 | "\x00\x00\x00\x42\x00\x1A" 375 | MSG_DELFILES_STR "\x00\x00" 376 | "\x00\x00\x00\x43\x00\x20" 377 | MSG_UNABLETOOPENZIP_STR "\x00\x00" 378 | "\x00\x00\x00\x44\x00\x1A" 379 | MSG_LHAERROR_STR "\x00" 380 | "\x00\x00\x00\x45\x00\x12" 381 | MSG_SKIPRETRYABORT_STR "\x00\x00" 382 | "\x00\x00\x00\x46\x00\x28" 383 | MSG_ARCHIVEMUSTHAVEENTRIES_STR "\x00" 384 | "\x00\x00\x00\x47\x00\x36" 385 | MSG_CONFIRMDELETE_STR "\x00" 386 | "\x00\x00\x00\x48\x00\x08" 387 | MSG_VIEWMODEBROWSER_STR "\x00" 388 | "\x00\x00\x00\x49\x00\x06" 389 | MSG_VIEWMODELIST_STR "\x00\x00" 390 | "\x00\x00\x00\x4A\x00\x0A" 391 | MSG_VIEWMODE_STR "\x00" 392 | "\x00\x00\x00\x4B\x00\x26" 393 | MSG_ERR_TREE_ALLOC_STR "\x00\x00" 394 | "\x00\x00\x00\x4C\x00\x10" 395 | MSG_NEWARCHIVE_STR "\x00\x00" 396 | "\x00\x00\x00\x4D\x00\x06" 397 | MSG_TYPE_STR "\x00" 398 | "\x00\x00\x00\x4E\x00\x08" 399 | MSG_CREATE_STR "\x00" 400 | "\x00\x00\x00\x4F\x00\x06" 401 | MSG_DIR_STR "\x00" 402 | "\x00\x00\x00\x50\x00\x0A" 403 | MSG_PARENT_STR "\x00\x00" 404 | "\x00\x00\x00\x51\x00\x0C" 405 | MSG_PACKEDSIZE_STR "\x00" 406 | "\x00\x00\x00\x52\x00\x34" 407 | MSG_SNAPSHOT_WARNING_STR "\x00\x00" 408 | "\x00\x00\x00\x53\x00\x20" 409 | MSG_ERR_NOTCPIP_STR "\x00\x00" 410 | "\x00\x00\x00\x54\x00\x1A" 411 | MSG_ERR_AMISSL_STR "\x00\x00" 412 | "\x00\x00\x00\x55\x00\x0E" 413 | MSG_ERR_UNKNOWN_STR "\x00" 414 | "\x00\x00\x00\x56\x00\x1C" 415 | MSG_NEWVERSION_STR "\x00\x00" 416 | "\x00\x00\x00\x57\x00\x1E" 417 | MSG_NONEWVERSION_STR "\x00" 418 | "\x00\x00\x00\x58\x00\x14" 419 | MSG_CHECKVERSION_STR "\x00" 420 | }; 421 | 422 | #endif /* CATCOMP_BLOCK */ 423 | 424 | 425 | /****************************************************************************/ 426 | 427 | 428 | 429 | #endif /* LOCALE_STRINGS_H_H */ 430 | -------------------------------------------------------------------------------- /src/misc.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | #include 18 | 19 | #include 20 | #include 21 | 22 | #include "win.h" 23 | #include "misc.h" 24 | #include "req.h" 25 | 26 | /** Useful functions **/ 27 | #ifndef __amigaos4__ 28 | struct Node *GetHead(struct List *list) 29 | { 30 | struct Node *res = NULL; 31 | 32 | if ((NULL != list) && (NULL != list->lh_Head->ln_Succ)) 33 | { 34 | res = list->lh_Head; 35 | } 36 | return res; 37 | } 38 | 39 | struct Node *GetPred(struct Node *node) 40 | { 41 | if (node->ln_Pred->ln_Pred == NULL) return NULL; 42 | return node->ln_Pred; 43 | } 44 | 45 | struct Node *GetSucc(struct Node *node) 46 | { 47 | if (node->ln_Succ->ln_Succ == NULL) return NULL; 48 | return node->ln_Succ; 49 | } 50 | #endif 51 | 52 | char *strdup(const char *s) 53 | { 54 | size_t len = strlen (s) + 1; 55 | char *result = (char*) malloc (len); 56 | if (result == (char*) 0) 57 | return (char*) 0; 58 | return (char*) memcpy (result, s, len); 59 | } 60 | 61 | #ifdef __amigaos4__ 62 | int32 recursive_scan(void *awin, CONST_STRPTR name) 63 | { 64 | int32 success = FALSE; 65 | APTR context = ObtainDirContextTags( EX_StringNameInput,name, 66 | EX_DoCurrentDir,TRUE, /* for recursion cd etc */ 67 | EX_DataFields,(EXF_NAME|EXF_LINK|EXF_TYPE), 68 | TAG_END); 69 | if(context) 70 | { 71 | struct ExamineData *dat; 72 | 73 | while((dat = ExamineDir(context))) 74 | { 75 | if( EXD_IS_LINK(dat) ) /* all link types - check first ! */ 76 | { 77 | if( EXD_IS_SOFTLINK(dat) ) 78 | { 79 | } 80 | else /* a hardlink */ 81 | { 82 | } 83 | } 84 | else if( EXD_IS_FILE(dat) ) 85 | { 86 | char *file; 87 | if(file = AllocVec(1024, MEMF_CLEAR)) { 88 | NameFromLock(GetCurrentDir(), file, 1024); 89 | AddPart(file, dat->Name, 1024); 90 | window_edit_add(awin, file); 91 | FreeVec(file); 92 | } 93 | } 94 | else if( EXD_IS_DIRECTORY(dat) ) 95 | { 96 | if( ! recursive_scan(awin, dat->Name ) ) /* recurse */ 97 | { 98 | break; 99 | } 100 | } 101 | } 102 | 103 | if( ERROR_NO_MORE_ENTRIES == IoErr() ) 104 | { 105 | success = TRUE; /* normal success exit */ 106 | } 107 | else 108 | { 109 | show_dos_error(IoErr(), awin); /* failure */ 110 | } 111 | 112 | } 113 | else 114 | { 115 | show_dos_error(IoErr(), awin); /* no context */ 116 | } 117 | 118 | ReleaseDirContext(context); /* NULL safe */ 119 | return(success); 120 | } 121 | 122 | BOOL object_is_dir(char *filename) 123 | { 124 | BOOL ret = FALSE; 125 | struct ExamineData *exd = ExamineObjectTags(EX_StringNameInput, filename, TAG_END); 126 | 127 | if(exd) { 128 | if(EXD_IS_DIRECTORY(exd)) ret = TRUE; 129 | 130 | FreeDosObject(DOS_EXAMINEDATA, exd); 131 | } 132 | 133 | return ret; 134 | } 135 | #else 136 | BOOL object_is_dir(BPTR lock) 137 | { 138 | BOOL ret = FALSE; 139 | struct FileInfoBlock *fib = AllocDosObject(DOS_FIB, NULL); 140 | 141 | if(fib) { 142 | if(Examine(lock, fib)) { 143 | if(fib->fib_DirEntryType > 0) ret = TRUE; 144 | } 145 | 146 | FreeDosObject(DOS_FIB, fib); 147 | } 148 | 149 | return ret; 150 | } 151 | 152 | void recursive_scan(void *awin, BPTR lock) 153 | { 154 | struct ExAllControl *eac = AllocDosObject(DOS_EXALLCONTROL, NULL); 155 | if (!eac) return; 156 | BOOL more; 157 | ULONG exalldata_size = sizeof(struct ExAllData) * 10; 158 | struct ExAllData *ead = AllocVec(exalldata_size, MEMF_CLEAR); 159 | 160 | eac->eac_LastKey = 0; 161 | do { 162 | more = ExAll(lock, ead, exalldata_size, ED_TYPE, eac); 163 | if ((!more) && (IoErr() != ERROR_NO_MORE_ENTRIES)) { 164 | /* ExAll failed abnormally */ 165 | show_dos_error(IoErr(), awin); 166 | break; 167 | } 168 | if (eac->eac_Entries == 0) { 169 | /* ExAll failed normally with no entries */ 170 | continue; /* ("more" is *usually* zero) */ 171 | } 172 | 173 | do { 174 | char *file; 175 | if(file = AllocVec(1024, MEMF_CLEAR)) { 176 | NameFromLock(lock, file, 1024); 177 | AddPart(file, ead->ed_Name, 1024); 178 | 179 | if(ead->ed_Type > 0) { /* dir? */ 180 | BPTR lock = Lock(file, ACCESS_READ); 181 | if(lock) { 182 | recursive_scan(awin, lock); 183 | UnLock(lock); 184 | } 185 | } else { 186 | window_edit_add(awin, file); 187 | } 188 | FreeVec(file); 189 | } 190 | 191 | /* get next ead */ 192 | ead = ead->ed_Next; 193 | } while (ead); 194 | } while (more); 195 | 196 | FreeDosObject(DOS_EXALLCONTROL, eac); 197 | FreeVec(ead); 198 | } 199 | #endif 200 | -------------------------------------------------------------------------------- /src/misc.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef MISC_H 16 | #define MISC_H 1 17 | 18 | #include 19 | #include 20 | 21 | #ifndef __amigaos4__ 22 | #define IsMinListEmpty(L) (L)->mlh_Head->mln_Succ == 0 23 | 24 | struct Node *GetHead(struct List *list); 25 | struct Node *GetPred(struct Node *node); 26 | struct Node *GetSucc(struct Node *node); 27 | 28 | #define IDoMethod DoMethod 29 | #endif 30 | 31 | #ifdef __amigaos4__ 32 | #define CurrentDir SetCurrentDir 33 | 34 | int32 recursive_scan(void *awin, CONST_STRPTR name); 35 | BOOL object_is_dir(char *filename); 36 | #else 37 | void recursive_scan(void *awin, BPTR lock); 38 | BOOL object_is_dir(BPTR lock); 39 | #endif 40 | 41 | char *strdup(const char *s); 42 | 43 | #endif 44 | -------------------------------------------------------------------------------- /src/mod_lha.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | 18 | #include 19 | #include 20 | 21 | #include 22 | #include 23 | 24 | #include "avalanche.h" 25 | #include "config.h" 26 | #include "locale.h" 27 | #include "module.h" 28 | #include "req.h" 29 | 30 | #ifdef __amigaos4__ 31 | #define DeleteFile Delete 32 | #endif 33 | 34 | static int mod_lha_error(void *awin, int err, char *file) 35 | { 36 | char msg[100]; 37 | 38 | snprintf(msg, 100, locale_get_string(MSG_LHAERROR), file); 39 | return open_error_req(msg, locale_get_string(MSG_SKIPRETRYABORT), awin); 40 | } 41 | 42 | static BOOL mod_lha_del(void *awin, char *archive, char **files, ULONG count) 43 | { 44 | int err; 45 | int user_choice; 46 | char cmd[1024]; 47 | 48 | for(int i = 0; i < count; i++) { 49 | snprintf(cmd, 1024, "lha -I d \"%s\" \"%s\"", archive, files[i]); 50 | 51 | err = SystemTags(cmd, 52 | SYS_Input, NULL, 53 | SYS_Output, NULL, 54 | SYS_Error, NULL, 55 | NP_Name, "Avalanche LhA Delete process", 56 | TAG_DONE); 57 | 58 | if(err != 0) { 59 | user_choice = mod_lha_error(awin, err, files[i]); 60 | 61 | switch(user_choice) { 62 | case 0: // abort 63 | return FALSE; 64 | break; 65 | 66 | case 1: // skip 67 | break; 68 | 69 | case 2: // retry 70 | i--; 71 | break; 72 | } 73 | } 74 | } 75 | 76 | return TRUE; 77 | } 78 | 79 | static BOOL mod_lha_add(void *awin, char *archive, char *file, char *dir) 80 | { 81 | int err; 82 | char cmd[1024]; 83 | snprintf(cmd, 1024, "lha -I a \"%s\" \"%s\"", archive, file); 84 | 85 | err = SystemTags(cmd, 86 | SYS_Input, NULL, 87 | SYS_Output, NULL, 88 | SYS_Error, NULL, 89 | NP_Name, "Avalanche LhA Add process", 90 | TAG_DONE); 91 | 92 | if(err != 0) { 93 | int user_choice = mod_lha_error(awin, err, file); 94 | 95 | switch(user_choice) { 96 | case 0: // abort 97 | return FALSE; 98 | break; 99 | 100 | case 1: // skip 101 | break; 102 | 103 | case 2: // retry 104 | return mod_lha_add(awin, archive, file, dir); 105 | break; 106 | } 107 | } 108 | 109 | return TRUE; 110 | } 111 | 112 | BOOL mod_lha_new(void *awin, char *archive) 113 | { 114 | BOOL ret = FALSE; 115 | struct avalanche_config *config = get_config(); 116 | ULONG new_arc_size = strlen(config->tmpdir) + strlen(NEW_ARC_NAME) + 2; 117 | char *tmpfile = AllocVec(new_arc_size, MEMF_CLEAR); 118 | 119 | if(tmpfile) { 120 | BPTR fh = 0; 121 | strcpy(tmpfile, config->tmpdir); 122 | AddPart(tmpfile, NEW_ARC_NAME, new_arc_size); 123 | 124 | if(fh = Open(tmpfile, MODE_NEWFILE)) { 125 | FPuts(fh, new_arc_text); 126 | Close(fh); 127 | 128 | ret = mod_lha_add(awin, archive, tmpfile, NULL); 129 | 130 | DeleteFile(tmpfile); 131 | } 132 | } 133 | 134 | return ret; 135 | } 136 | 137 | void mod_lha_register(struct module_functions *funcs) 138 | { 139 | funcs->add = mod_lha_add; 140 | funcs->del = mod_lha_del; 141 | } 142 | -------------------------------------------------------------------------------- /src/mod_zip.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | 17 | #include 18 | #include 19 | 20 | #include 21 | 22 | #ifdef __amigaos4__ 23 | #include 24 | #include 25 | #endif 26 | 27 | #include "libs.h" 28 | #include "locale.h" 29 | #include "module.h" 30 | #include "req.h" 31 | 32 | #include "Avalanche_rev.h" 33 | 34 | #ifdef __amigaos4__ 35 | static void mod_zip_show_error(void *awin, zip_t *zip) 36 | { 37 | open_error_req(zip_error_strerror(zip_get_error(zip)), locale_get_string(MSG_OK), awin); 38 | } 39 | 40 | static BOOL mod_zip_del(void *awin, char *archive, char **files, ULONG count) 41 | { 42 | int err = 0; 43 | zip_t *zip = zip_open(archive, 0, &err); 44 | 45 | if(zip) { 46 | for(int i = 0; i < count; i++) { 47 | zip_int64_t index = zip_name_locate(zip, files[i], 0); 48 | if(index == -1) { 49 | mod_zip_show_error(awin, zip); 50 | zip_discard(zip); 51 | return FALSE; 52 | } 53 | 54 | err = zip_delete(zip, index); 55 | if(err == -1) { 56 | mod_zip_show_error(awin, zip); 57 | zip_discard(zip); 58 | return FALSE; 59 | } 60 | } 61 | 62 | err = zip_close(zip); 63 | if(err == -1) { 64 | mod_zip_show_error(awin, zip); 65 | zip_discard(zip); 66 | return FALSE; 67 | } 68 | return TRUE; 69 | } else { 70 | open_error_req(zip_error_strerror(&err), locale_get_string(MSG_OK), awin); 71 | } 72 | 73 | return FALSE; 74 | } 75 | 76 | static BOOL mod_zip_add_file(void *awin, zip_t *zip, char *file, char *dir, BOOL new) 77 | { 78 | int err = 0; 79 | char *fullfile = NULL; 80 | zip_source_t *src = NULL; 81 | 82 | if(new == FALSE) { 83 | src = zip_source_file(zip, file, 0, -1); 84 | if(src == NULL) { 85 | mod_zip_show_error(awin, zip); 86 | zip_discard(zip); 87 | return FALSE; 88 | } 89 | } else { 90 | src = zip_source_buffer(zip, new_arc_text, strlen(new_arc_text), 0); 91 | if(src == NULL) { 92 | mod_zip_show_error(awin, zip); 93 | zip_discard(zip); 94 | return FALSE; 95 | } 96 | } 97 | 98 | if(dir != NULL) { 99 | ULONG fullfile_len = strlen(FilePart(file)) + strlen(dir) + 1; 100 | fullfile = AllocVec(fullfile_len, MEMF_CLEAR); 101 | 102 | if(fullfile) { 103 | strcpy(fullfile, dir); 104 | AddPart(fullfile, FilePart(file), fullfile_len); 105 | } 106 | } else { 107 | fullfile = FilePart(file); 108 | } 109 | 110 | err = zip_file_add(zip, fullfile, src, 0); 111 | 112 | if(dir && fullfile) FreeVec(fullfile); 113 | 114 | if(err == -1) { 115 | mod_zip_show_error(awin, zip); 116 | zip_discard(zip); 117 | return FALSE; 118 | } 119 | 120 | err = zip_close(zip); 121 | if(err == -1) { 122 | mod_zip_show_error(awin, zip); 123 | zip_discard(zip); 124 | return FALSE; 125 | } 126 | return TRUE; 127 | } 128 | 129 | static BOOL mod_zip_add(void *awin, char *archive, char *file, char *dir) 130 | { 131 | int err = 0; 132 | zip_t *zip = zip_open(archive, 0, &err); 133 | 134 | if(zip) { 135 | return mod_zip_add_file(awin, zip, file, dir, FALSE); 136 | } else { 137 | open_error_req(zip_error_strerror(&err), locale_get_string(MSG_OK), awin); 138 | } 139 | 140 | return FALSE; 141 | } 142 | #endif 143 | 144 | BOOL mod_zip_new(void *awin, char *archive) 145 | { 146 | #ifdef __amigaos4__ 147 | int err = 0; 148 | 149 | if(!libs_zip_init()) return FALSE; 150 | 151 | zip_t *zip = zip_open(archive, ZIP_CREATE, &err); 152 | 153 | if(zip) { 154 | return mod_zip_add_file(awin, zip, NEW_ARC_NAME, NULL, TRUE); 155 | } else { 156 | open_error_req(zip_error_strerror(&err), locale_get_string(MSG_OK), awin); 157 | } 158 | #endif 159 | return FALSE; 160 | } 161 | 162 | void mod_zip_register(struct module_functions *funcs) 163 | { 164 | #ifdef __amigaos4__ 165 | if(libs_zip_init()) { 166 | funcs->add = mod_zip_add; 167 | funcs->del = mod_zip_del; 168 | } 169 | #endif 170 | } 171 | -------------------------------------------------------------------------------- /src/module.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | 17 | #include "avalanche.h" 18 | #include "config.h" 19 | #include "libs.h" 20 | #include "module.h" 21 | #include "win.h" 22 | 23 | #include "deark.h" 24 | #include "xad.h" 25 | #include "xfd.h" 26 | #include "xvs.h" 27 | 28 | char *new_arc_text = "Created with " VERS "\0"; 29 | 30 | /*** Virus Scanning ***/ 31 | ULONG module_vscan(void *awin, char *file, UBYTE *buf, ULONG len, BOOL delete) 32 | { 33 | long res = 0; 34 | struct avalanche_config *config = get_config(); 35 | 36 | if(config->virus_scan) { 37 | if(buf == NULL) { 38 | res = xvs_scan(file, delete, awin); 39 | } else { 40 | res = xvs_scan_buffer(buf, len, awin); 41 | } 42 | 43 | if((res == -1) || (res == -3)) { 44 | config->virus_scan = FALSE; 45 | config->disable_vscan_menu = TRUE; 46 | 47 | } 48 | } 49 | 50 | return res; 51 | } 52 | 53 | /*** Extraction ***/ 54 | const char *module_get_item_filename(void *awin, void *userdata) 55 | { 56 | struct module_functions *mf = window_get_module_funcs(awin); 57 | 58 | if(mf->get_filename) return mf->get_filename(userdata, awin); 59 | 60 | return NULL; 61 | } 62 | 63 | LONG *module_get_crunched_size(void *awin, void *userdata) 64 | { 65 | struct module_functions *mf = window_get_module_funcs(awin); 66 | 67 | if(mf->get_crunchsize) return mf->get_crunchsize(userdata, awin); 68 | 69 | return NULL; 70 | } 71 | 72 | void module_free(void *awin) 73 | { 74 | struct module_functions *mf = window_get_module_funcs(awin); 75 | 76 | if(mf->free) mf->free(awin); 77 | } 78 | 79 | const char *module_get_format(void *awin) 80 | { 81 | struct module_functions *mf = window_get_module_funcs(awin); 82 | 83 | if(mf->get_format) return mf->get_format(awin); 84 | 85 | return NULL; 86 | } 87 | 88 | const char *module_get_subformat(void *awin) 89 | { 90 | struct module_functions *mf = window_get_module_funcs(awin); 91 | 92 | if(mf->get_subformat) return mf->get_subformat(awin); 93 | 94 | return NULL; 95 | } 96 | 97 | const char *module_get_error(void *awin, long code) 98 | { 99 | struct module_functions *mf = window_get_module_funcs(awin); 100 | 101 | if(mf->get_error) return mf->get_error(awin, code); 102 | 103 | return NULL; 104 | } 105 | 106 | const char *module_get_read_module(void *awin) 107 | { 108 | struct module_functions *mf = window_get_module_funcs(awin); 109 | 110 | return mf->module; 111 | } 112 | 113 | long module_extract(void *awin, void *node, void *archive, void *newdest) 114 | { 115 | long ret = 0; 116 | 117 | switch(window_get_archiver(awin)) { 118 | case ARC_XAD: 119 | if(node == NULL) { 120 | ret = xad_extract(awin, archive, newdest, window_get_lblist(awin), window_get_lbnode); 121 | } else { 122 | ULONG pud = 0; 123 | ret = xad_extract_file(awin, archive, newdest, node, window_get_lbnode, &pud); 124 | } 125 | break; 126 | case ARC_XFD: 127 | ret = xfd_extract(awin, archive, newdest); 128 | break; 129 | case ARC_DEARK: 130 | if(node == NULL) { 131 | ret = deark_extract(awin, archive, newdest, window_get_lblist(awin), window_get_lbnode); 132 | } else { 133 | ret = deark_extract_file(awin, archive, newdest, node, window_get_lbnode); 134 | } 135 | break; 136 | } 137 | 138 | return ret; 139 | } 140 | 141 | long module_extract_array(void *awin, void **array, ULONG total_items, void *dest) 142 | { 143 | long ret = 0; 144 | 145 | switch(window_get_archiver(awin)) { 146 | case ARC_XAD: 147 | ret = xad_extract_array(awin, total_items, dest, array, array_get_userdata); 148 | break; 149 | case ARC_DEARK: 150 | ret = deark_extract_array(awin, total_items, dest, array, array_get_userdata); 151 | break; 152 | } 153 | 154 | return ret; 155 | } 156 | 157 | void module_exit(void) 158 | { 159 | /* Close libraries associated with all modules */ 160 | /* TODO: This only happens at program exit, 161 | * keep track of whether modules are being used 162 | * and close the libs early. */ 163 | xad_exit(); 164 | xfd_exit(); 165 | } 166 | 167 | BOOL module_recog(void* fullfilename) 168 | { 169 | BOOL found = FALSE; 170 | found = xad_recog(fullfilename); 171 | if(found == FALSE) found = xfd_recog(fullfilename); 172 | 173 | return found; 174 | } 175 | 176 | static void module_extract_register(void *awin, struct module_functions *mf) 177 | { 178 | /* Remove existing registration */ 179 | mf->module[0] = 'N'; 180 | mf->module[1] = '/'; 181 | mf->module[2] = 'A'; 182 | mf->module[3] = 0; 183 | 184 | mf->get_filename = NULL; 185 | mf->get_crunchsize = NULL; 186 | mf->get_format = NULL; 187 | mf->get_subformat = NULL; 188 | mf->get_error = NULL; 189 | mf->free = NULL; 190 | 191 | /* Register correct module */ 192 | switch(window_get_archiver(awin)) { 193 | case ARC_XAD: 194 | xad_register(mf); 195 | break; 196 | case ARC_XFD: 197 | xfd_register(mf); 198 | break; 199 | case ARC_DEARK: 200 | deark_register(mf); 201 | break; 202 | } 203 | } 204 | 205 | /*** Editing ***/ 206 | 207 | BOOL module_has_add(void *awin) 208 | { 209 | struct module_functions *mf = window_get_module_funcs(awin); 210 | 211 | if(mf->add != NULL) return TRUE; 212 | return FALSE; 213 | } 214 | 215 | void module_register(void *awin, struct module_functions *mf) 216 | { 217 | module_extract_register(awin, mf); 218 | 219 | const char *format = module_get_format(awin); 220 | 221 | /* TODO: close libs if possible, see module_close() */ 222 | 223 | /* Remove existing registration */ 224 | mf->add = NULL; 225 | mf->del = NULL; 226 | 227 | /* Register correct module */ 228 | if(format && (strcmp(format, "Zip") == 0)) mod_zip_register(mf); 229 | if(format && (strcmp(format, "LhA") == 0)) mod_lha_register(mf); 230 | } 231 | -------------------------------------------------------------------------------- /src/module.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef MODULE_H 16 | #define MODULE_H 17 | 18 | #include 19 | 20 | /* For new archive creation */ 21 | #include "Avalanche_rev.h" 22 | extern char *new_arc_text; 23 | #define NEW_ARC_NAME ".readme" 24 | 25 | struct module_functions { 26 | /* Extraction */ 27 | char module[4]; 28 | const char *(*get_filename)(void *userdata, void *awin); 29 | const LONG *(*get_crunchsize)(void *userdata, void *awin); 30 | const char *(*get_format)(void *awin); 31 | const char *(*get_subformat)(void *awin); 32 | const char *(*get_error)(void *awin, long code); 33 | void (*free)(void *awin); 34 | 35 | /* Editing */ 36 | BOOL (*add)(void *awin, char *archive, char *file, char *dir); /* Returns TRUE on success */ 37 | BOOL (*del)(void *awin, char *archive, char **files, ULONG count); /* Returns TRUE on success */ 38 | }; 39 | 40 | /* Virus scan */ 41 | ULONG module_vscan(void *awin, char *file, UBYTE *buf, ULONG len, BOOL delete); 42 | 43 | /* Extraction */ 44 | const char *module_get_item_filename(void *awin, void *userdata); 45 | LONG *module_get_crunched_size(void *awin, void *userdata); 46 | void module_free(void *awin); 47 | const char *module_get_format(void *awin); 48 | const char *module_get_subformat(void *awin); 49 | const char *module_get_read_module(void *awin); 50 | const char *module_get_error(void *awin, long code); 51 | long module_extract(void *awin, void *node, void *archive, void *newdest); 52 | long module_extract_array(void *awin, void **array, ULONG total_items, void *dest); 53 | void module_exit(void); 54 | BOOL module_recog(void* fullfilename); 55 | 56 | /* Editing */ 57 | BOOL module_has_add(void *awin); 58 | 59 | /* Create new */ 60 | BOOL mod_lha_new(void *awin, char *archive); 61 | BOOL mod_zip_new(void *awin, char *archive); 62 | 63 | /*** Register modules ***/ 64 | void module_register(void *awin, struct module_functions *mf); 65 | 66 | /*** Register extended modules ***/ 67 | void mod_zip_register(struct module_functions *funcs); 68 | void mod_lha_register(struct module_functions *funcs); 69 | 70 | #endif 71 | -------------------------------------------------------------------------------- /src/new.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | #include 18 | 19 | #include 20 | #include 21 | #include 22 | #include 23 | 24 | #ifndef __amigaos4__ 25 | #include 26 | #endif 27 | #include 28 | 29 | #include 30 | #include 31 | #include 32 | #include 33 | #include 34 | #include 35 | 36 | #include 37 | #include 38 | #include 39 | #include 40 | 41 | #include 42 | #include 43 | 44 | #include "avalanche.h" 45 | #include "new.h" 46 | #include "libs.h" 47 | #include "locale.h" 48 | #include "module.h" 49 | #include "win.h" 50 | 51 | #include "Avalanche_rev.h" 52 | 53 | enum { 54 | GID_N_MAIN = 0, 55 | GID_N_ARCHIVE, 56 | GID_N_TYPE, 57 | GID_N_CREATE, 58 | GID_N_CANCEL, 59 | GID_N_LAST 60 | }; 61 | 62 | enum { 63 | WID_MAIN = 0, 64 | WID_LAST 65 | }; 66 | 67 | enum { 68 | OID_MAIN = 0, 69 | OID_LAST 70 | }; 71 | 72 | STRPTR type_opts[] = { 73 | "LhA", 74 | #ifdef __amigaos4__ 75 | "Zip", 76 | #endif 77 | NULL 78 | }; 79 | 80 | static struct Window *windows[WID_LAST]; 81 | static struct Gadget *gadgets[GID_N_LAST]; 82 | static Object *objects[OID_LAST]; 83 | static struct MsgPort *naw_port = NULL; 84 | static void *newarc_parent = NULL; 85 | 86 | static void newarc_window_close(void) 87 | { 88 | RA_CloseWindow(objects[OID_MAIN]); 89 | windows[WID_MAIN] = NULL; 90 | DisposeObject(objects[OID_MAIN]); 91 | 92 | DeleteMsgPort(naw_port); 93 | naw_port = NULL; 94 | 95 | newarc_parent = NULL; 96 | } 97 | 98 | static void newarc_req_archive(void) 99 | { 100 | ULONG res; 101 | 102 | if(res = DoMethod((Object *)gadgets[GID_N_ARCHIVE], GFILE_REQUEST, windows[WID_MAIN])) { 103 | SetGadgetAttrs(gadgets[GID_N_CREATE], windows[WID_MAIN], NULL, 104 | GA_Disabled, FALSE, 105 | TAG_DONE); 106 | } 107 | } 108 | 109 | static void newarc_create(void) 110 | { 111 | BOOL ret = FALSE; 112 | ULONG data; 113 | char *arc_type; 114 | char *archive; 115 | 116 | GetAttr(CHOOSER_Selected, gadgets[GID_N_TYPE], (ULONG *)&data); 117 | arc_type = type_opts[data]; 118 | 119 | GetAttr(GETFILE_FullFile, gadgets[GID_N_ARCHIVE], (APTR)&archive); 120 | 121 | if(archive == NULL) return; 122 | 123 | switch(data) { 124 | case 0: // LhA 125 | ret = mod_lha_new(newarc_parent, archive); 126 | break; 127 | 128 | case 1: // Zip 129 | ret = mod_zip_new(newarc_parent, archive); 130 | break; 131 | } 132 | 133 | if(ret) { 134 | window_update_archive(newarc_parent, archive); 135 | window_req_open_archive(newarc_parent, get_config(), TRUE); 136 | } 137 | 138 | } 139 | 140 | /* Public functions */ 141 | void newarc_window_open(void *awin) 142 | { 143 | if(windows[WID_MAIN]) { // already open 144 | WindowToFront(windows[WID_MAIN]); 145 | return; 146 | } 147 | 148 | if(naw_port = CreateMsgPort()) { 149 | /* Create the window object */ 150 | objects[OID_MAIN] = WindowObj, 151 | WA_ScreenTitle, VERS, 152 | WA_Title, VERS, 153 | WA_Activate, TRUE, 154 | WA_DepthGadget, TRUE, 155 | WA_DragBar, TRUE, 156 | WA_CloseGadget, TRUE, 157 | WA_SizeGadget, FALSE, 158 | WINDOW_SharedPort, naw_port, 159 | WINDOW_Position, WPOS_CENTERSCREEN, 160 | WINDOW_ParentGroup, gadgets[GID_N_MAIN] = LayoutVObj, 161 | //LAYOUT_DeferLayout, TRUE, 162 | LAYOUT_SpaceOuter, TRUE, 163 | LAYOUT_AddChild, LayoutVObj, 164 | LAYOUT_AddChild, LayoutVObj, 165 | LAYOUT_AddChild, gadgets[GID_N_ARCHIVE] = GetFileObj, 166 | GA_ID, GID_N_ARCHIVE, 167 | GA_RelVerify, TRUE, 168 | GETFILE_TitleText, locale_get_string( MSG_SELECTARCHIVE ) , 169 | GETFILE_DoSaveMode, TRUE, 170 | GETFILE_DrawersOnly, FALSE, 171 | GETFILE_ReadOnly, TRUE, 172 | End, 173 | CHILD_WeightedHeight, 0, 174 | CHILD_Label, LabelObj, 175 | LABEL_Text, locale_get_string( MSG_ARCHIVE ) , 176 | LabelEnd, 177 | 178 | LAYOUT_AddChild, gadgets[GID_N_TYPE] = ChooserObj, 179 | GA_ID, GID_N_TYPE, 180 | GA_RelVerify, TRUE, 181 | GA_Selected, 0, 182 | CHOOSER_PopUp, TRUE, 183 | CHOOSER_LabelArray, type_opts, 184 | End, 185 | CHILD_Label, LabelObj, 186 | LABEL_Text, locale_get_string(MSG_TYPE), 187 | LabelEnd, 188 | LayoutEnd, 189 | LAYOUT_AddChild, LayoutHObj, 190 | LAYOUT_AddChild, gadgets[GID_N_CREATE] = ButtonObj, 191 | GA_ID, GID_N_CREATE, 192 | GA_RelVerify, TRUE, 193 | GA_Text, locale_get_string( MSG_CREATE ), 194 | GA_Disabled, TRUE, 195 | ButtonEnd, 196 | LAYOUT_AddChild, gadgets[GID_N_CANCEL] = ButtonObj, 197 | GA_ID, GID_N_CANCEL, 198 | GA_RelVerify, TRUE, 199 | GA_Text, locale_get_string( MSG_CANCEL ), 200 | ButtonEnd, 201 | CHILD_WeightedHeight, 0, 202 | LayoutEnd, 203 | LayoutEnd, 204 | EndGroup, 205 | EndWindow; 206 | 207 | if(objects[OID_MAIN]) { 208 | windows[WID_MAIN] = (struct Window *)RA_OpenWindow(objects[OID_MAIN]); 209 | 210 | newarc_parent = awin; 211 | } 212 | } 213 | 214 | return; 215 | } 216 | 217 | ULONG newarc_window_get_signal(void) 218 | { 219 | if(naw_port) { 220 | return (1L << naw_port->mp_SigBit); 221 | } else { 222 | return 0; 223 | } 224 | } 225 | 226 | ULONG newarc_window_handle_input(UWORD *code) 227 | { 228 | return RA_HandleInput(objects[OID_MAIN], code); 229 | } 230 | 231 | BOOL newarc_window_handle_input_events(ULONG result, UWORD code) 232 | { 233 | long ret = 0; 234 | ULONG done = FALSE; 235 | 236 | switch (result & WMHI_CLASSMASK) { 237 | case WMHI_CLOSEWINDOW: 238 | newarc_window_close(); 239 | done = TRUE; 240 | break; 241 | 242 | case WMHI_GADGETUP: 243 | switch (result & WMHI_GADGETMASK) { 244 | case GID_N_ARCHIVE: 245 | newarc_req_archive(); 246 | break; 247 | case GID_N_CREATE: 248 | newarc_create(); 249 | newarc_window_close(); 250 | done = TRUE; 251 | break; 252 | case GID_N_CANCEL: 253 | newarc_window_close(); 254 | done = TRUE; 255 | break; 256 | } 257 | break; 258 | } 259 | 260 | return done; 261 | } 262 | 263 | void newarc_window_close_if_associated(void *awin) 264 | { 265 | if(awin == newarc_parent) newarc_window_close(); 266 | } 267 | -------------------------------------------------------------------------------- /src/new.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2023 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef AVALANCHE_NEW_H 16 | #define AVALANCHE_NEW_H 1 17 | 18 | void newarc_window_open(void *awin); 19 | ULONG newarc_window_get_signal(void); 20 | ULONG newarc_window_handle_input(UWORD *code); 21 | BOOL newarc_window_handle_input_events(ULONG result, UWORD code); 22 | void newarc_window_close_if_associated(void *awin); 23 | #endif 24 | -------------------------------------------------------------------------------- /src/os3/Makefile: -------------------------------------------------------------------------------- 1 | CC := vc +aos68k 2 | CFLAGS := -c99 -O3 -Inetinclude: 3 | LIBS := -lamiga 4 | OBJDIR := objs_os3 5 | VPATH := .. 6 | 7 | OBJS := avalanche.o arexx.o config.o deark.o http.o libs.o locale.o misc.o module.o mod_lha.o mod_zip.o new.o req.o win.o xad.o xfd.o xvs.o 8 | DEPS := avalanche_rev.h avalanche.h arexx.h config.h deark.h http.h libs.h locale.h locale_strings.h misc.h module.h new.h req.h win.h xad.h xfd.h xvs.h 9 | 10 | all: Avalanche 11 | 12 | %.o: %.c $(DEPS) 13 | $(CC) $(CFLAGS) -c -o $@ $< 14 | 15 | Avalanche: $(OBJS) 16 | $(CC) $(CFLAGS) -o $@ $^ $(LIBS) 17 | 18 | clean: 19 | delete #?.o 20 | delete Avalanche 21 | -------------------------------------------------------------------------------- /src/os4/Makefile: -------------------------------------------------------------------------------- 1 | CC := vc +newlib 2 | CFLAGS := -static -O3 -D__USE_INLINE__ -ISDK:local/common/include -ISDK:include/netinclude 3 | LIBS := 4 | VPATH := .. 5 | 6 | OBJS := avalanche.o arexx.o config.o deark.o http.o libs.o locale.o misc.o module.o mod_lha.o mod_zip.o new.o req.o win.o xad.o xfd.o xvs.o 7 | DEPS := avalanche_rev.h avalanche.h arexx.h config.h deark.h http.h libs.h locale.h locale_strings.h misc.h module.h new.h req.h win.h xad.h xfd.h xvs.h 8 | 9 | all: AvalanchePPC 10 | 11 | %.o: %.c $(DEPS) 12 | $(CC) $(CFLAGS) -c -o $@ $< 13 | 14 | AvalanchePPC: $(OBJS) 15 | $(CC) $(CFLAGS) -o $@ $^ $(LIBS) 16 | 17 | clean: 18 | delete #?.o 19 | delete AvalanchePPC 20 | -------------------------------------------------------------------------------- /src/os4/Makefile.gcc: -------------------------------------------------------------------------------- 1 | CC := gcc -std=c99 2 | CFLAGS := -gstabs -D__USE_INLINE__ 3 | LIBS := 4 | VPATH := .. 5 | 6 | OBJS := avalanche.o arexx.o config.o http.o libs.o locale.o misc.o module.o mod_lha.o mod_zip.o new.o req.o win.o xad.o xfd.o xvs.o 7 | DEPS := avalanche_rev.h avalanche.h arexx.h config.h http.h libs.h locale.h locale_strings.h misc.h module.h new.h req.h win.h xad.h xfd.h xvs.h 8 | 9 | all: AvalanchePPC 10 | 11 | %.o: %.c $(DEPS) 12 | $(CC) $(CFLAGS) -c -o $@ $< 13 | 14 | AvalanchePPC: $(OBJS) 15 | $(CC) $(CFLAGS) -o $@ $^ $(LIBS) 16 | 17 | clean: 18 | delete #?.o 19 | delete AvalanchePPC 20 | -------------------------------------------------------------------------------- /src/req.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | 18 | #include 19 | #include 20 | #include 21 | #include 22 | 23 | #include 24 | #include 25 | 26 | #include 27 | 28 | #include "avalanche.h" 29 | #include "libs.h" 30 | #include "locale.h" 31 | #include "module.h" 32 | #include "req.h" 33 | #include "win.h" 34 | 35 | #include "Avalanche_rev.h" 36 | 37 | #define MSG_COPYRIGHT VERS " (" DATE ")\n" "(c) 2022-3 Chris Young\n\33uhttps://github.com/chris-y/avalanche\33n\n\n" 38 | 39 | void open_info_req(const char *message, const char *buttons, void *awin) 40 | { 41 | Object *obj = RequesterObj, 42 | REQ_TitleText, VERS, 43 | REQ_Type, REQTYPE_INFO, 44 | REQ_Image, REQIMAGE_INFO, 45 | REQ_BodyText, message, 46 | REQ_GadgetText, buttons, 47 | End; 48 | 49 | if(obj) { 50 | OpenRequester(obj, window_get_window(awin)); 51 | DisposeObject(obj); 52 | } 53 | } 54 | 55 | void show_about(void *awin) 56 | { 57 | int len = strlen(MSG_COPYRIGHT) + strlen(locale_get_string( MSG_GPL )) + 1; 58 | char *msg = AllocVec(len, MEMF_PRIVATE | MEMF_CLEAR); 59 | 60 | if(msg) { 61 | snprintf(msg, len, "%s%s", MSG_COPYRIGHT, locale_get_string(MSG_GPL)); 62 | open_info_req(msg, locale_get_string(MSG_OK), awin); 63 | FreeVec(msg); 64 | } 65 | } 66 | 67 | int open_error_req(const char *message, const char *button, void *awin) 68 | { 69 | int ret = 0; 70 | 71 | Object *obj = RequesterObj, 72 | REQ_TitleText, VERS, 73 | REQ_Type, REQTYPE_INFO, 74 | REQ_Image, REQIMAGE_ERROR, 75 | REQ_BodyText, message, 76 | REQ_GadgetText, button, 77 | End; 78 | 79 | if(obj) { 80 | ret = OpenRequester(obj, window_get_window(awin)); 81 | DisposeObject(obj); 82 | } else { 83 | printf( locale_get_string( MSG_UNABLETOOPENREQUESTERTOSHOWERRORS ) , message, button); 84 | } 85 | 86 | return ret; 87 | } 88 | 89 | void show_dos_error(long code, void *awin) 90 | { 91 | char message[100]; 92 | 93 | Fault(code, NULL, message, 100); 94 | 95 | open_error_req(message, locale_get_string(MSG_OK), awin); 96 | } 97 | 98 | void show_error(long code, void *awin) 99 | { 100 | char message[100]; 101 | 102 | if(code == -1) { 103 | /* TODO: check this, code is the same for xfd */ 104 | snprintf(message, 100, locale_get_string( MSG_UNABLETOOPENLIBRARY ), "xadmaster.library", 12 ); 105 | } else { 106 | char *err_msg = module_get_error(awin, code); 107 | if (err_msg == NULL) return; 108 | snprintf(message, 100, "%s", err_msg); 109 | } 110 | 111 | open_error_req(message, locale_get_string(MSG_OK), awin); 112 | } 113 | 114 | ULONG ask_yesno_req(void *awin, const char *message) 115 | { 116 | int ret = 1; 117 | 118 | Object *obj = RequesterObj, 119 | REQ_TitleText, VERS, 120 | REQ_Type, REQTYPE_INFO, 121 | REQ_Image, REQIMAGE_WARNING, 122 | REQ_BodyText, message , 123 | REQ_GadgetText, locale_get_string( MSG_YESNO ) , 124 | End; 125 | 126 | if(obj) { 127 | ret = OpenRequester(obj, window_get_window(awin)); 128 | DisposeObject(obj); 129 | } 130 | return ret; 131 | } 132 | 133 | ULONG ask_quithide_req(void) 134 | { 135 | int ret = 1; 136 | 137 | Object *obj = RequesterObj, 138 | REQ_TitleText, VERS, 139 | REQ_Type, REQTYPE_INFO, 140 | REQ_Image, REQIMAGE_WARNING, 141 | REQ_BodyText, locale_get_string( MSG_LASTWINDOWCLOSED ) , 142 | REQ_GadgetText, locale_get_string( MSG_QUITHIDECANCEL ) , 143 | End; 144 | 145 | if(obj) { 146 | ret = OpenRequester(obj, NULL); 147 | DisposeObject(obj); 148 | } 149 | return ret; 150 | } 151 | 152 | ULONG warning_req(void *awin, const char *message) 153 | { 154 | int ret = 1; 155 | 156 | Object *obj = RequesterObj, 157 | REQ_TitleText, VERS, 158 | REQ_Type, REQTYPE_INFO, 159 | REQ_Image, REQIMAGE_WARNING, 160 | REQ_BodyText, message , 161 | REQ_GadgetText, locale_get_string( MSG_OK ) , 162 | End; 163 | 164 | if(obj) { 165 | ret = OpenRequester(obj, window_get_window(awin)); 166 | DisposeObject(obj); 167 | } 168 | return ret; 169 | } 170 | 171 | ULONG ask_question(void *awin, const char *q, const char *f) 172 | { 173 | char message[200]; 174 | int ret = 0; 175 | 176 | snprintf(message, 200, q, f); 177 | 178 | Object *obj = RequesterObj, 179 | REQ_TitleText, VERS, 180 | REQ_Type, REQTYPE_INFO, 181 | REQ_Image, REQIMAGE_QUESTION, 182 | REQ_BodyText, message, 183 | REQ_GadgetText, locale_get_string( MSG_YESYESTOALLNONOTOALLABORT ) , 184 | End; 185 | 186 | if(obj) { 187 | ret = OpenRequester(obj, window_get_window(awin)); 188 | DisposeObject(obj); 189 | } else { 190 | printf( locale_get_string( MSG_UNABLETOOPENREQUESTERTOSHOWERRORS ) , message, ""); 191 | } 192 | 193 | return ret; 194 | } 195 | 196 | ULONG ask_password(void *awin, const char *pw, ULONG pwlen) 197 | { 198 | int ret = 0; 199 | 200 | Object *obj = RequesterObj, 201 | REQ_TitleText, VERS, 202 | REQ_Type, REQTYPE_STRING, 203 | REQ_Image, REQIMAGE_QUESTION, 204 | REQS_Invisible, TRUE, 205 | REQS_Buffer, pw, 206 | REQS_MaxChars, pwlen, 207 | REQ_BodyText, locale_get_string( MSG_ARCHIVEISENCRYPTEDPLEASEENTERPASSWORD ) , 208 | REQ_GadgetText, locale_get_string( MSG_OKCANCEL ) , 209 | End; 210 | 211 | if(obj) { 212 | ret = OpenRequester(obj, window_get_window(awin)); 213 | DisposeObject(obj); 214 | } else { 215 | printf( locale_get_string( MSG_UNABLETOOPENREQUESTERTOASKPASSWORD ) ); 216 | } 217 | 218 | return ret; 219 | } 220 | 221 | void req_show_arc_info(void *awin) 222 | { 223 | char message[100]; 224 | const char *modname = module_get_read_module(awin); 225 | 226 | if(modname == NULL) return; 227 | 228 | const char *subf = module_get_subformat(awin); 229 | 230 | if(subf) { 231 | snprintf(message, 100, "%s (%s) - %s", module_get_format(awin), subf, modname); 232 | } else { 233 | snprintf(message, 100, "%s - %s", module_get_format(awin), modname); 234 | } 235 | 236 | open_info_req(message, locale_get_string(MSG_OK), awin); 237 | } 238 | -------------------------------------------------------------------------------- /src/req.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef REQ_H 16 | #define REQ_H 1 17 | 18 | #include 19 | 20 | ULONG ask_question(void *awin, const char *q, const char *f); 21 | ULONG ask_password(void *awin, const char *pw, ULONG pwlen); 22 | ULONG ask_yesno_req(void *awin, const char *message); 23 | ULONG ask_quithide_req(void); 24 | void show_error(long code, void *awin); 25 | void show_dos_error(long code, void *awin); 26 | void show_about(void *awin); 27 | int open_error_req(const char *message, const char *button, void *awin); 28 | void open_info_req(const char *message, const char *buttons, void *awin); 29 | void req_show_arc_info(void *awin); 30 | ULONG warning_req(void *awin, const char *message); 31 | #endif 32 | -------------------------------------------------------------------------------- /src/win.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef WIN_H 16 | #define WIN_H 1 17 | 18 | #include 19 | 20 | #include "avalanche.h" 21 | 22 | struct MsgPort; 23 | struct module_functions; 24 | 25 | /* Basic window functions */ 26 | void *window_create(struct avalanche_config *config, char *archive, struct MsgPort *winport, struct MsgPort *appport); 27 | void window_open(void *awin, struct MsgPort *appwin_mp); 28 | void window_close(void *awin, BOOL iconify); 29 | void window_dispose(void *awin); 30 | 31 | /* Update window */ 32 | void window_update_archive(void *awin, char *archive); 33 | void window_update_sourcedir(void *awin, char *sourcedir); 34 | void window_toggle_hbrowser(void *awin, BOOL h_browser); 35 | void window_fuelgauge_update(void *awin, ULONG size, ULONG total_size); 36 | void window_modify_all_list(void *awin, ULONG select); 37 | 38 | /* Handle events */ 39 | void window_req_open_archive(void *awin, struct avalanche_config *config, BOOL refresh_only); 40 | char *window_req_dest(void *awin); 41 | ULONG window_handle_input(void *awin, UWORD *code); 42 | ULONG window_handle_input_events(void *awin, struct avalanche_config *config, ULONG result, struct MsgPort *appwin_mp, UWORD code, struct MsgPort *winport, struct MsgPort *AppPort); 43 | 44 | /* Get info */ 45 | void *window_get_window(void *awin); 46 | Object *window_get_object(void *awin); 47 | void *window_get_lbnode(void *awin, struct Node *node); 48 | struct List *window_get_lblist(void *awin); 49 | ULONG window_get_archiver(void *awin); 50 | void *array_get_userdata(void *awin, void *arc_entry); 51 | struct module_functions *window_get_module_funcs(void *awin); 52 | 53 | /* Modify archive */ 54 | //BOOL window_edit_add_wbarg(void *awin, struct WBArg *wbarg); 55 | BOOL window_edit_add(void *awin, char *file); 56 | 57 | /* Misc */ 58 | void window_disable_gadgets(void *awin, BOOL disable); 59 | BOOL check_abort(void *awin); 60 | void window_reset_count(void *awin); 61 | void fill_menu_labels(void); 62 | long extract(void *awin, char *archive, char *newdest, struct Node *node); 63 | 64 | /* Archiver userdata */ 65 | void *window_get_archive_userdata(void *awin); 66 | void window_set_archive_userdata(void *awin, void *userdata); 67 | void *window_alloc_archive_userdata(void *awin, ULONG size); 68 | void window_free_archive_userdata(void *awin); 69 | #endif 70 | -------------------------------------------------------------------------------- /src/xad.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | #include 18 | 19 | #include 20 | #include 21 | 22 | #include "avalanche.h" 23 | #include "config.h" 24 | #include "libs.h" 25 | #include "locale.h" 26 | #include "module.h" 27 | #include "req.h" 28 | #include "win.h" 29 | #include "xad.h" 30 | 31 | #ifdef __amigaos4__ 32 | #define SetFileDate SetDate 33 | #define xadMasterBase XadMasterBase 34 | #endif 35 | 36 | enum { 37 | PUD_NONE = 0, 38 | PUD_ABORT = 1, 39 | PUD_SKIP = 2, 40 | PUD_OVER = 3 41 | }; 42 | 43 | enum { 44 | XNONE = 0, 45 | XFILE, 46 | XDISK, 47 | XDISKFILE 48 | }; 49 | 50 | struct xad_hookdata { 51 | ULONG *pud; 52 | void *awin; 53 | }; 54 | 55 | struct xad_userdata { 56 | struct xadArchiveInfo *ai; 57 | int arctype; 58 | char *pw; 59 | }; 60 | 61 | static void xad_free_ai(struct xadArchiveInfo *a) 62 | { 63 | xadFreeInfo(a); 64 | xadFreeObjectA(a, NULL); 65 | } 66 | 67 | static void xad_free_pw(void *awin) 68 | { 69 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 70 | 71 | if(xu->pw) { 72 | for(int i = 0; i < strlen(xu->pw); i++) 73 | xu->pw[i] = '\0'; 74 | 75 | FreeVec(xu->pw); 76 | xu->pw = NULL; 77 | } 78 | 79 | } 80 | 81 | static void xad_free(void *awin) 82 | { 83 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 84 | if(xu) { 85 | if (xu->ai) { 86 | xad_free_ai(xu->ai); 87 | xu->ai = NULL; 88 | } 89 | 90 | xad_free_pw(awin); 91 | 92 | } 93 | 94 | window_free_archive_userdata(awin); 95 | } 96 | 97 | void xad_exit(void) 98 | { 99 | libs_xad_exit(); 100 | } 101 | 102 | static const char *xad_error(void *awin, long code) 103 | { 104 | /* suppress user break messages */ 105 | if(code != XADERR_BREAK) 106 | return xadGetErrorText((ULONG)code); 107 | 108 | return NULL; 109 | } 110 | 111 | ULONG get_xad_ver(void) 112 | { 113 | struct Library *lib = (struct Library *)xadMasterBase; 114 | return lib->lib_Version; 115 | } 116 | 117 | static BOOL xad_is_dir(struct xadFileInfo *fi) 118 | { 119 | if(fi->xfi_Flags & XADFIF_DIRECTORY) return TRUE; 120 | if((get_xad_ver() == 12) && (fi->xfi_FileName[strlen(fi->xfi_FileName)-1] == '/')) return TRUE; 121 | return FALSE; 122 | } 123 | 124 | static ULONG xad_get_fileprotection(void *xfi) 125 | { 126 | ULONG protbits; 127 | struct xadFileInfo *fi = (struct xadFileInfo *)xfi; 128 | 129 | xadConvertProtection(XAD_PROTFILEINFO, fi, 130 | XAD_GETPROTAMIGA, &protbits, 131 | TAG_DONE); 132 | 133 | return protbits; 134 | } 135 | 136 | ULONG xad_get_filedate(void *xfi, struct ClockData *cd, void *awin) 137 | { 138 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 139 | 140 | if(xu && xu->arctype == XDISK) return 0; 141 | if(xfi == NULL) return 0; 142 | 143 | struct xadFileInfo *fi = (struct xadFileInfo *)xfi; 144 | 145 | return xadConvertDates(XAD_DATEXADDATE, &fi->xfi_Date, 146 | XAD_GETDATECLOCKDATA, cd, 147 | XAD_MAKELOCALDATE, TRUE, 148 | TAG_DONE); 149 | } 150 | 151 | static LONG *xad_get_crunchsize(void *userdata, void *awin) 152 | { 153 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 154 | 155 | if(xu && xu->arctype == XDISK) return NULL; 156 | if(userdata == NULL) return NULL; 157 | 158 | struct xadFileInfo *fi = (struct xadFileInfo *)userdata; 159 | 160 | return (LONG *)&fi->xfi_CrunchSize; 161 | } 162 | 163 | static const char *xad_get_filename(void *userdata, void *awin) 164 | { 165 | if(userdata == NULL) return NULL; 166 | 167 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 168 | 169 | if(xu && (xu->arctype == XDISK)) return "disk.img"; 170 | 171 | struct xadFileInfo *fi = (struct xadFileInfo *)userdata; /* userdata is userdata from the node! */ 172 | 173 | return fi->xfi_FileName; 174 | } 175 | 176 | #ifdef __amigaos4__ 177 | static ULONG xad_progress(struct Hook *h, APTR obj, struct xadProgressInfo *xpi) 178 | #else 179 | static ULONG __saveds xad_progress(__reg("a0") struct Hook *h, __reg("a2") APTR obj, __reg("a1") struct xadProgressInfo *xpi) 180 | #endif 181 | { 182 | struct xad_hookdata *xhd = (struct xad_hookdata *)h->h_Data; 183 | ULONG *pud = xhd->pud; 184 | ULONG res; 185 | 186 | switch(xpi->xpi_Mode) { 187 | case XADPMODE_ASK: 188 | if(xpi->xpi_Status & XADPIF_OVERWRITE) { 189 | if(*pud == PUD_SKIP) return (XADPIF_OK | XADPIF_SKIP); 190 | if(*pud == PUD_OVER) return (XADPIF_OK | XADPIF_OVERWRITE); 191 | res = ask_question(xhd->awin, locale_get_string( MSG_ALREADYEXISTSOVERWRITE ) , xpi->xpi_FileName); 192 | switch(res) { 193 | case 0: // Abort 194 | *pud = PUD_ABORT; 195 | return 0; 196 | break; 197 | 198 | case 2: // Yes to all 199 | *pud = PUD_OVER; 200 | case 1: // Yes 201 | return (XADPIF_OK | XADPIF_OVERWRITE); 202 | break; 203 | 204 | case 4: // No to all 205 | *pud = PUD_SKIP; 206 | case 3: // No 207 | return (XADPIF_OK | XADPIF_SKIP); 208 | break; 209 | } 210 | } 211 | break; 212 | 213 | case XADPMODE_ERROR: 214 | if(xpi->xpi_Error != XADERR_SKIP) 215 | /* We did show error here, but we also show afterwards 216 | * show_error(xpi->xpi_Error, xhd->awin); */ 217 | break; 218 | 219 | case XADPMODE_PROGRESS: 220 | if(xpi->xpi_FileInfo) { 221 | window_fuelgauge_update(xhd->awin, xpi->xpi_CurrentSize, xpi->xpi_FileInfo->xfi_Size); 222 | } else if(xpi->xpi_DiskInfo) { 223 | window_fuelgauge_update(xhd->awin, xpi->xpi_CurrentSize, 224 | xpi->xpi_DiskInfo->xdi_TotalSectors * xpi->xpi_DiskInfo->xdi_SectorSize); 225 | } 226 | break; 227 | 228 | default: 229 | //printf("%d\n", xpi->xpi_Mode); 230 | break; 231 | } 232 | 233 | if(check_abort(xhd->awin)) { 234 | *pud = PUD_ABORT; 235 | return 0; 236 | } 237 | 238 | return XADPIF_OK; 239 | } 240 | 241 | static const char *xad_get_arc_format(void *awin) 242 | { 243 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 244 | if(!xu->ai) return NULL; 245 | 246 | return xu->ai->xai_Client->xc_ArchiverName; 247 | } 248 | 249 | static const char *xad_get_arc_subformat(void *awin) 250 | { 251 | char *type; 252 | 253 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 254 | if(!xu->ai) return NULL; 255 | 256 | switch(xu->arctype) { 257 | case XFILE: 258 | type = locale_get_string( MSG_FILEARCHIVE ) ; 259 | break; 260 | case XDISK: 261 | type = locale_get_string( MSG_DISKARCHIVE ) ; 262 | break; 263 | case XDISKFILE: 264 | type = locale_get_string( MSG_DISKIMAGE ) ; 265 | break; 266 | default: 267 | type = locale_get_string( MSG_UNKNOWN ) ; 268 | break; 269 | } 270 | 271 | return type; 272 | } 273 | 274 | BOOL xad_recog(char *file) 275 | { 276 | BPTR fh = 0; 277 | ULONG len; 278 | struct xadClient *xc = NULL; 279 | 280 | libs_xad_init(); 281 | if(xadMasterBase == NULL) return FALSE; 282 | 283 | #ifndef __amigaos4__ 284 | ULONG xadrs = xadMasterBase->xmb_RecogSize; 285 | #else 286 | const struct xadSystemInfo *xadsi = xadGetSystemInfo(); 287 | ULONG xadrs = xadsi->xsi_RecogSize; 288 | #endif 289 | 290 | UBYTE *buf = AllocVec(xadrs, MEMF_ANY); 291 | if(buf == NULL) return FALSE; 292 | 293 | if(fh = Open(file, MODE_OLDFILE)) { 294 | len = Read(fh, buf, xadrs); 295 | Close(fh); 296 | 297 | xc = xadRecogFile(len, buf, 298 | //XAD_IGNOREFLAGS, XADAIF_DISKARCHIVE, 299 | TAG_DONE); 300 | } 301 | 302 | FreeVec(buf); 303 | 304 | if(xc == NULL) return FALSE; 305 | 306 | return TRUE; 307 | } 308 | 309 | long xad_info(char *file, struct avalanche_config *config, void *awin, void(*addnode)(char *name, LONG *size, BOOL dir, ULONG item, ULONG total, void *userdata, struct avalanche_config *config, void *awin)) 310 | { 311 | long err = 0; 312 | struct xadFileInfo *fi; 313 | struct xadDiskInfo *di; 314 | struct xadArchiveInfo *dai = NULL; 315 | struct xadArchiveInfo *ai = NULL; 316 | ULONG total = 0; 317 | ULONG i = 0; 318 | ULONG size; 319 | BOOL fs = !config->ignorefs; 320 | 321 | libs_xad_init(); 322 | if(xadMasterBase == NULL) return -1; 323 | 324 | xad_free(awin); 325 | 326 | struct xad_userdata *xu = (struct xad_userdata *)window_alloc_archive_userdata(awin, sizeof(struct xad_userdata)); 327 | if(xu == NULL) return -2; 328 | 329 | xu->ai = xadAllocObjectA(XADOBJ_ARCHIVEINFO, NULL); 330 | ai = xu->ai; 331 | xu->arctype = XNONE; 332 | 333 | if(ai) { 334 | if((err = xadGetInfo(ai, 335 | XAD_INFILENAME, file, 336 | TAG_DONE)) == 0) { 337 | if(ai->xai_DiskInfo) xu->arctype = XDISK; 338 | if(ai->xai_FileInfo) xu->arctype = XFILE; /* We only support one of file/disk so file preferred */ 339 | 340 | } 341 | 342 | if(fs && ((xu->arctype == XNONE) || (xu->arctype == XDISK))) { 343 | dai = xadAllocObjectA(XADOBJ_ARCHIVEINFO, NULL); 344 | 345 | if(xu->arctype == XNONE) { 346 | err = xadGetDiskInfo(dai, 347 | XAD_INFILENAME, file, 348 | TAG_DONE); 349 | } else { 350 | struct TagItem ti[2]; 351 | ti[0].ti_Tag = XAD_INFILENAME; 352 | ti[0].ti_Data = (ULONG)file; 353 | ti[1].ti_Tag = TAG_DONE; 354 | 355 | err = xadGetDiskInfo(dai, 356 | XAD_INDISKARCHIVE, &ti, 357 | TAG_DONE); 358 | } 359 | 360 | if(err == 0) { 361 | xu->arctype = XDISKFILE; 362 | xad_free_ai(ai); 363 | ai = dai; 364 | xu->ai = dai; 365 | } else { 366 | xad_free_ai(dai); 367 | } 368 | } 369 | 370 | if(xu->arctype == XDISK) { 371 | /* Count entries (disks) */ 372 | /* We only support archives which have disks or files, not mixed */ 373 | di = ai->xai_DiskInfo; 374 | while(di) { 375 | total++; 376 | di = di->xdi_Next; 377 | } 378 | 379 | /* Add to list */ 380 | di = ai->xai_DiskInfo; 381 | while(di) { 382 | size = di->xdi_SectorSize * di->xdi_TotalSectors; 383 | addnode("disk.img", &size, 0, i, total, di, config, awin); 384 | i++; 385 | di = di->xdi_Next; 386 | } 387 | 388 | } else if (xu->arctype != XNONE) { 389 | /* Count entries (files) */ 390 | fi = ai->xai_FileInfo; 391 | while(fi) { 392 | total++; 393 | fi = fi->xfi_Next; 394 | } 395 | 396 | /* Add to list */ 397 | fi = ai->xai_FileInfo; 398 | while(fi) { 399 | addnode(fi->xfi_FileName, &fi->xfi_Size, 400 | (fi->xfi_Flags & XADFIF_DIRECTORY), i, total, fi, config, awin); 401 | i++; 402 | fi = fi->xfi_Next; 403 | } 404 | } 405 | } 406 | 407 | if(err != 0) xad_free(awin); 408 | 409 | return err; 410 | } 411 | 412 | static long xad_extract_file_private(void *awin, char *dest, struct xad_userdata *xu, struct xadDiskInfo *di, struct xadFileInfo *fi, ULONG *pud) 413 | { 414 | long err = 0; 415 | 416 | struct DateStamp ds; 417 | char *fn = NULL; 418 | 419 | struct xadArchiveInfo *ai = xu->ai; 420 | 421 | struct xad_hookdata xhd; 422 | xhd.pud = pud; 423 | xhd.awin = awin; 424 | 425 | struct Hook progress_hook; 426 | progress_hook.h_Entry = xad_progress; 427 | progress_hook.h_SubEntry = NULL; 428 | progress_hook.h_Data = &xhd; 429 | 430 | 431 | if(fi || di) { 432 | char destfile[1024]; 433 | strncpy(destfile, dest, 1023); 434 | destfile[1023] = 0; 435 | 436 | if(fi) { 437 | fn = fi->xfi_FileName; 438 | } else { 439 | fn = "disk.img"; 440 | } 441 | 442 | if(AddPart(destfile, fn, 1024)) { 443 | if((di) || (!xad_is_dir(fi))) { 444 | if(((fi && (fi->xfi_Flags & XADFIF_CRYPTED)) || (di && (di->xdi_Flags & XADDIF_CRYPTED))) && (xu->pw == NULL)) { 445 | xu->pw = AllocVec(100, MEMF_CLEAR); 446 | err = ask_password(awin, xu->pw, 100); 447 | if(err == 0) { 448 | FreeVec(xu->pw); 449 | xu->pw = NULL; 450 | } 451 | } 452 | 453 | switch(xu->arctype) { 454 | case XFILE: 455 | err = xadFileUnArc(ai, 456 | XAD_ENTRYNUMBER, fi->xfi_EntryNumber, 457 | XAD_MAKEDIRECTORY, TRUE, 458 | XAD_OUTFILENAME, destfile, 459 | XAD_PASSWORD, xu->pw, 460 | XAD_PROGRESSHOOK, &progress_hook, 461 | TAG_DONE); 462 | break; 463 | 464 | case XDISK: 465 | err = xadDiskUnArc(ai, XAD_ENTRYNUMBER, di->xdi_EntryNumber, 466 | XAD_OUTFILENAME, destfile, 467 | XAD_PASSWORD, xu->pw, 468 | XAD_PROGRESSHOOK, &progress_hook, 469 | TAG_DONE); 470 | break; 471 | 472 | case XDISKFILE: 473 | err = xadDiskFileUnArc(ai, 474 | XAD_ENTRYNUMBER, fi->xfi_EntryNumber, 475 | XAD_MAKEDIRECTORY, TRUE, 476 | XAD_OUTFILENAME, destfile, 477 | XAD_PASSWORD, xu->pw, 478 | XAD_PROGRESSHOOK, &progress_hook, 479 | TAG_DONE); 480 | break; 481 | } 482 | 483 | if(err != XADERR_OK) { 484 | if(err == XADERR_PASSWORD) xad_free_pw(awin); 485 | return err; 486 | } 487 | 488 | if(*pud == PUD_ABORT) { 489 | if(xu->pw) FreeVec(xu->pw); 490 | xu->pw = NULL; 491 | return XADERR_BREAK; 492 | } 493 | 494 | if(err == XADERR_OK) { 495 | if(fi) module_vscan(awin, destfile, NULL, fi->xfi_Size, TRUE); 496 | if(di) module_vscan(awin, destfile, NULL, di->xdi_SectorSize * di->xdi_TotalSectors, TRUE); 497 | } 498 | 499 | if(fi) { 500 | err = xadConvertDates(XAD_DATEXADDATE, &fi->xfi_Date, 501 | XAD_GETDATEDATESTAMP, &ds, 502 | XAD_MAKELOCALDATE, TRUE, 503 | TAG_DONE); 504 | 505 | if(err != XADERR_OK) return err; 506 | 507 | SetProtection(destfile, xad_get_fileprotection(fi)); 508 | SetFileDate(destfile, &ds); 509 | if(fi && fi->xfi_Comment) SetComment(destfile, fi->xfi_Comment); 510 | } 511 | } 512 | } 513 | } 514 | 515 | return err; 516 | } 517 | 518 | 519 | long xad_extract_file(void *awin, char *file, char *dest, struct Node *node, void *(getnode)(void *awin, struct Node *node), ULONG *pud) 520 | { 521 | long err; 522 | struct xadFileInfo *fi = NULL; 523 | struct xadDiskInfo *di = NULL; 524 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 525 | if(xu->arctype == XDISK) { 526 | di = (struct xadDiskInfo *)getnode(awin, node); 527 | } else { 528 | fi = (struct xadFileInfo *)getnode(awin, node); 529 | } 530 | 531 | return xad_extract_file_private(awin, dest, xu, di, fi, pud); 532 | } 533 | 534 | /* returns 0 on success */ 535 | long xad_extract(void *awin, char *file, char *dest, struct List *list, void *(getnode)(void *awin, struct Node *node)) 536 | { 537 | long err = XADERR_OK; 538 | struct Node *fnode; 539 | ULONG pud = 0; 540 | 541 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 542 | 543 | if(xu->ai) { 544 | for(fnode = list->lh_Head; fnode->ln_Succ; fnode=fnode->ln_Succ) { 545 | err = xad_extract_file(awin, file, dest, fnode, getnode, &pud); 546 | if(err != XADERR_OK) { 547 | return err; 548 | } 549 | } 550 | } 551 | 552 | return err; 553 | } 554 | 555 | long xad_extract_array(void *awin, ULONG total_items, char *dest, void **array, void *(getuserdata)(void *awin, void *arc_entry)) 556 | { 557 | long err = XADERR_OK; 558 | ULONG pud = 0; 559 | struct xadFileInfo *fi = NULL; 560 | struct xadDiskInfo *di = NULL; 561 | 562 | struct xad_userdata *xu = (struct xad_userdata *)window_get_archive_userdata(awin); 563 | 564 | if(xu->ai) { 565 | for(int i = 0; i < total_items; i++) { 566 | if(xu->arctype == XDISK) { 567 | di = (struct xadDiskInfo *)getuserdata(awin, array[i]); 568 | } else { 569 | fi = (struct xadFileInfo *)getuserdata(awin, array[i]); 570 | } 571 | 572 | if((di == NULL) && (fi == NULL)) continue; 573 | 574 | err = xad_extract_file_private(awin, dest, xu, di, fi, &pud); 575 | if(err != XADERR_OK) { 576 | return err; 577 | } 578 | } 579 | } 580 | 581 | return err; 582 | } 583 | 584 | 585 | void xad_register(struct module_functions *funcs) 586 | { 587 | funcs->module[0] = 'X'; 588 | funcs->module[1] = 'A'; 589 | funcs->module[2] = 'D'; 590 | funcs->module[3] = 0; 591 | 592 | funcs->get_filename = xad_get_filename; 593 | funcs->free = xad_free; 594 | funcs->get_format = xad_get_arc_format; 595 | funcs->get_subformat = xad_get_arc_subformat; 596 | funcs->get_error = xad_error; 597 | funcs->get_crunchsize = xad_get_crunchsize; 598 | } 599 | -------------------------------------------------------------------------------- /src/xad.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef XAD_H 16 | #define XAD_H 1 17 | 18 | #include 19 | 20 | #include "avalanche.h" 21 | 22 | void xad_exit(void); 23 | ULONG get_xad_ver(void); 24 | ULONG xad_get_filedate(void *xfi, struct ClockData *cd, void *awin); 25 | BOOL xad_recog(char *file); 26 | long xad_info(char *file, struct avalanche_config *config, void *awin, void(*addnode)(char *name, LONG *size, BOOL dir, ULONG item, ULONG total, void *userdata, struct avalanche_config *config, void *awin)); 27 | 28 | long xad_extract(void *awin, char *file, char *dest, struct List *list, void *(getnode)(void *awin, struct Node *node)); 29 | long xad_extract_file(void *awin, char *file, char *dest, struct Node *node, void *(getnode)(void *awin, struct Node *node), ULONG *pud); 30 | long xad_extract_array(void *awin, ULONG total_items, char *dest, void **array, void *(getuserdata)(void *awin, void *arc_entry)); 31 | 32 | void xad_register(struct module_functions *funcs); 33 | #endif 34 | -------------------------------------------------------------------------------- /src/xfd.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | #include 18 | 19 | #include 20 | #include 21 | #include 22 | 23 | #include "avalanche.h" 24 | #include "libs.h" 25 | #include "locale.h" 26 | #include "misc.h" 27 | #include "module.h" 28 | #include "req.h" 29 | #include "win.h" 30 | #include "xfd.h" 31 | 32 | #define XFD_ERR_LIBOPEN -1 33 | #define XFD_ERR_MEM -2 34 | #define XFD_ERR_FILEOPEN -3 35 | 36 | struct xfd_userdata { 37 | struct xfdBufferInfo *bi; 38 | char *fn; 39 | UBYTE *buffer; 40 | }; 41 | 42 | static void xfd_free(void *awin) 43 | { 44 | struct xfd_userdata *xu = (struct xfd_userdata *)window_get_archive_userdata(awin); 45 | if(xu) { 46 | if(xu->bi != NULL) xfdFreeObject(xu->bi); 47 | if(xu->buffer != NULL) FreeVec(xu->buffer); 48 | if(xu->fn != NULL) { 49 | free(xu->fn); 50 | xu->fn = NULL; 51 | } 52 | } 53 | 54 | window_free_archive_userdata(awin); 55 | } 56 | 57 | static const char *xfd_get_filename(void *userdata, void *awin) 58 | { 59 | return userdata; 60 | } 61 | 62 | static LONG *xfd_get_crunchsize(void *userdata, void *awin) 63 | { 64 | struct xfd_userdata *xu = (struct xfd_userdata *)window_get_archive_userdata(awin); 65 | if(!xu->bi) return NULL; 66 | 67 | return (LONG *)&xu->bi->xfdbi_SourceBufLen; 68 | } 69 | 70 | static const char *xfd_get_arc_format(void *awin) 71 | { 72 | struct xfd_userdata *xu = (struct xfd_userdata *)window_get_archive_userdata(awin); 73 | if(!xu->bi) return NULL; 74 | 75 | return xu->bi->xfdbi_PackerName; 76 | } 77 | 78 | static const char *xfd_error(void *awin, long code) 79 | { 80 | if(code < 0) { 81 | switch(code) { 82 | case XFD_ERR_MEM: 83 | return locale_get_string(MSG_OUTOFMEMORY); 84 | break; 85 | case XFD_ERR_FILEOPEN: 86 | return locale_get_string(MSG_UNABLETOOPENFILE); 87 | break; 88 | } 89 | } 90 | 91 | return NULL; 92 | } 93 | 94 | BOOL xfd_recog(char *file) 95 | { 96 | BPTR fh = 0; 97 | ULONG len; 98 | BOOL res = FALSE; 99 | 100 | libs_xfd_init(); 101 | if(xfdMasterBase == NULL) return FALSE; 102 | 103 | struct xfdMasterBase *xfdmb = (struct xfdMasterBase *)xfdMasterBase; 104 | 105 | struct xfdBufferInfo *xfdbi = xfdAllocObject(XFDOBJ_BUFFERINFO); 106 | if(xfdbi == NULL) return FALSE; 107 | 108 | UBYTE *buf = AllocVec(xfdmb->xfdm_MinBufferSize, MEMF_ANY); 109 | if(buf == NULL) { 110 | xfdFreeObject(xfdbi); 111 | return FALSE; 112 | } 113 | 114 | if(fh = Open(file, MODE_OLDFILE)) { 115 | len = Read(fh, buf, xfdmb->xfdm_MinBufferSize); 116 | Close(fh); 117 | 118 | xfdbi->xfdbi_SourceBuffer = buf; 119 | xfdbi->xfdbi_SourceBufLen = len; 120 | xfdbi->xfdbi_Flags = XFDFB_RECOGEXTERN; 121 | 122 | res = xfdRecogBuffer(xfdbi); 123 | } 124 | 125 | FreeVec(buf); 126 | xfdFreeObject(xfdbi); 127 | 128 | return res; 129 | } 130 | 131 | long xfd_info(char *file, void *awin, void(*addnode)(char *name, LONG *size, BOOL dir, ULONG item, ULONG total, void *userdata, struct avalanche_config *config, void *awin)) 132 | { 133 | BPTR fh = 0; 134 | ULONG len; 135 | BOOL res = FALSE; 136 | 137 | libs_xfd_init(); 138 | if(xfdMasterBase == NULL) return XFD_ERR_LIBOPEN; 139 | 140 | struct xfdMasterBase *xfdmb = (struct xfdMasterBase *)xfdMasterBase; 141 | 142 | xfd_free(awin); 143 | struct xfd_userdata *xu = (struct xfd_userdata *)window_alloc_archive_userdata(awin, sizeof(struct xfd_userdata)); 144 | 145 | xu->bi = xfdAllocObject(XFDOBJ_BUFFERINFO); 146 | if(xu->bi == NULL) return XFD_ERR_MEM; 147 | struct xfdBufferInfo *bi = xu->bi; 148 | 149 | if(fh = Open(file, MODE_OLDFILE)) { 150 | #ifdef __amigaos4__ 151 | len = (ULONG)GetFileSize(fh); 152 | #else 153 | Seek(fh, 0, OFFSET_END); 154 | len = Seek(fh, 0, OFFSET_BEGINNING); 155 | #endif 156 | 157 | xu->buffer = AllocVec(len, MEMF_ANY); 158 | if(xu->buffer == NULL) { 159 | Close(fh); 160 | xfdFreeObject(xu->bi); 161 | xu->bi = NULL; 162 | return XFD_ERR_MEM; 163 | } 164 | 165 | len = Read(fh, xu->buffer, len); 166 | Close(fh); 167 | 168 | bi->xfdbi_SourceBuffer = xu->buffer; 169 | bi->xfdbi_SourceBufLen = len; 170 | bi->xfdbi_Flags = XFDFB_RECOGEXTERN; 171 | 172 | res = xfdRecogBuffer(bi); 173 | } 174 | 175 | if(res == TRUE) { 176 | xu->fn = strdup(FilePart(file)); 177 | /* Add to list */ 178 | addnode(xu->fn, &bi->xfdbi_FinalTargetLen, 0, 0, 1, xu->fn, get_config(), awin); 179 | 180 | return 0; 181 | } 182 | 183 | xfd_free(awin); 184 | return XFD_ERR_FILEOPEN; 185 | } 186 | 187 | long xfd_extract(void *awin, char *file, char *dest) 188 | { 189 | BPTR fh; 190 | char *pw = NULL; 191 | ULONG pwlen = 100; 192 | ULONG err; 193 | ULONG res = 1; 194 | 195 | struct xfd_userdata *xu = (struct xfd_userdata *)window_get_archive_userdata(awin); 196 | struct xfdBufferInfo *bi = xu->bi; 197 | 198 | if(bi->xfdbi_PackerFlags & XFDPFF_PASSWORD) { 199 | if(bi->xfdbi_MaxSpecialLen > 0) 200 | pwlen = bi->xfdbi_MaxSpecialLen; 201 | pw = AllocVec(pwlen, MEMF_CLEAR); 202 | err = ask_password(awin, pw, pwlen); 203 | if(err == 0) { 204 | FreeVec(pw); 205 | pw = NULL; 206 | } else { 207 | bi->xfdbi_Special = pw; 208 | } 209 | } 210 | 211 | if(xfdDecrunchBuffer(bi) == TRUE) { 212 | if(module_vscan(awin, NULL, bi->xfdbi_TargetBuffer, bi->xfdbi_TargetBufSaveLen, TRUE) < 4) { 213 | char destfile[1024]; 214 | strncpy(destfile, dest, 1023); 215 | destfile[1023] = 0; 216 | if(AddPart(destfile, xu->fn, 1024)) { 217 | if(fh = Open(destfile, MODE_OLDFILE)) { 218 | res = ask_question(awin, locale_get_string( MSG_ALREADYEXISTSOVERWRITE ) , xu->fn); 219 | Close(fh); 220 | } 221 | 222 | if((res == 1) || (res == 2)) { 223 | if(fh = Open(destfile, MODE_NEWFILE)) { 224 | Write(fh, bi->xfdbi_TargetBuffer, bi->xfdbi_TargetBufSaveLen); 225 | Close(fh); 226 | } 227 | } 228 | } 229 | } 230 | FreeMem(bi->xfdbi_TargetBuffer, bi->xfdbi_TargetBufLen); 231 | } else { 232 | open_error_req( locale_get_string( MSG_ERRORDECRUNCHING ) , locale_get_string( MSG_OK ) , awin); 233 | } 234 | return 0; 235 | } 236 | 237 | void xfd_exit(void) 238 | { 239 | libs_xfd_exit(); 240 | } 241 | 242 | void xfd_register(struct module_functions *funcs) 243 | { 244 | funcs->module[0] = 'X'; 245 | funcs->module[1] = 'F'; 246 | funcs->module[2] = 'D'; 247 | funcs->module[3] = 0; 248 | 249 | funcs->get_filename = xfd_get_filename; 250 | funcs->get_crunchsize = xfd_get_crunchsize; 251 | funcs->free = xfd_free; 252 | funcs->get_format = xfd_get_arc_format; 253 | funcs->get_subformat = NULL; 254 | funcs->get_error = xfd_error; 255 | } 256 | -------------------------------------------------------------------------------- /src/xfd.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022-3 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef XFD_H 16 | #define XFD_H 1 17 | 18 | void xfd_exit(void); 19 | BOOL xfd_recog(char *file); 20 | long xfd_info(char *file, void *awin, void(*addnode)(char *name, LONG *size, BOOL dir, ULONG item, ULONG total, void *userdata, struct avalanche_config *config, void *awin)); 21 | long xfd_extract(void *awin, char *file, char *dest); 22 | 23 | void xfd_register(struct module_functions *funcs); 24 | 25 | #endif 26 | -------------------------------------------------------------------------------- /src/xvs.c: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #include 16 | #include 17 | #include 18 | 19 | #include 20 | #include 21 | 22 | #include "avalanche.h" 23 | #include "libs.h" 24 | #include "locale.h" 25 | #include "req.h" 26 | #include "xvs.h" 27 | 28 | static long xvs_init(void *awin) 29 | { 30 | if(xvsBase == NULL) { 31 | char *msg; 32 | libs_xvs_init(); 33 | if(xvsBase == NULL) { 34 | int len = strlen(locale_get_string( MSG_UNABLETOOPENLIBRARY )) + strlen(locale_get_string( MSG_VIRUSSCANNINGWILLBEDISABLED )) + strlen("xvs.library") + 4; 35 | if(msg = AllocVec(len, MEMF_CLEAR)) { 36 | snprintf(msg, len, locale_get_string( MSG_UNABLETOOPENLIBRARY ), "xvs.library", 33); 37 | strncat(msg, locale_get_string( MSG_VIRUSSCANNINGWILLBEDISABLED ), len); 38 | open_error_req(msg, locale_get_string( MSG_OK ), awin ); 39 | FreeVec(msg); 40 | } 41 | return -1; 42 | } 43 | 44 | if(xvsSelfTest() == FALSE) { 45 | int len = strlen(locale_get_string( MSG_XVSLIBRARYFAILEDSELFTEST )) + strlen(locale_get_string( MSG_VIRUSSCANNINGWILLBEDISABLED )) + 2; 46 | if(msg = AllocVec(len, MEMF_CLEAR)) { 47 | snprintf(msg, len, "%s\n%s", locale_get_string( MSG_XVSLIBRARYFAILEDSELFTEST ), locale_get_string( MSG_VIRUSSCANNINGWILLBEDISABLED )); 48 | open_error_req(msg, locale_get_string( MSG_OK ), awin ); 49 | FreeVec(msg); 50 | } 51 | return -3; 52 | } 53 | } 54 | return 0; 55 | } 56 | 57 | static long xvs_scan_virus(char *file, UBYTE *buf, ULONG len, BOOL delete, void *awin) 58 | { 59 | struct xvsFileInfo *xvsfi = NULL; 60 | ULONG result; 61 | 62 | long err = xvs_init(awin); 63 | if(err != 0) return err; 64 | 65 | xvsfi = xvsAllocObject(XVSOBJ_FILEINFO); 66 | if(xvsfi == NULL) { 67 | FreeVec(buf); 68 | open_error_req( locale_get_string( MSG_OUTOFMEMORYSCANNINGFILE ) , locale_get_string( MSG_OK ), awin ); 69 | return -2; 70 | } 71 | 72 | xvsfi->xvsfi_File = buf; 73 | xvsfi->xvsfi_FileLen = len; 74 | 75 | result = xvsCheckFile(xvsfi); 76 | 77 | if((result == XVSFT_DATAVIRUS) || (result == XVSFT_FILEVIRUS) || (result == XVSFT_LINKVIRUS)) { 78 | char message[200]; 79 | 80 | if(file) { 81 | if(delete == TRUE) { 82 | BOOL deleted = DeleteFile(file); 83 | 84 | if(deleted) { 85 | snprintf(message, 200, locale_get_string( MSG_VIRUSFOUNDETECTIONNAME ) , file, xvsfi->xvsfi_Name); 86 | strncat(message, locale_get_string(MSG_FILEHASBEENDELETED), 200); 87 | } else { 88 | snprintf(message, 200, locale_get_string( MSG_VIRUSFOUNDETECTIONNAME ) , file, xvsfi->xvsfi_Name); 89 | strncat(message, locale_get_string(MSG_FILECOULDNOTBEDELETED), 200); 90 | } 91 | } else { 92 | snprintf(message, 200, locale_get_string( MSG_VIRUSFOUNDETECTIONNAME ) , file, xvsfi->xvsfi_Name); 93 | } 94 | } else { 95 | snprintf(message, 200, locale_get_string( MSG_VIRUSFOUNDETECTIONNAME ) , "----", xvsfi->xvsfi_Name); 96 | } 97 | 98 | open_error_req(message, locale_get_string( MSG_OK ), awin ); 99 | } else { 100 | result = 0; // clean 101 | } 102 | 103 | xvsFreeObject(xvsfi); 104 | 105 | return result; 106 | } 107 | 108 | long xvs_scan_buffer(UBYTE *buf, ULONG len, void *awin) 109 | { 110 | return xvs_scan_virus(NULL, buf, len, FALSE, awin); 111 | } 112 | 113 | long xvs_scan(char *file, BOOL delete, void *awin) 114 | { 115 | UBYTE *buffer = NULL; 116 | BPTR fh = 0; 117 | long res = 0; 118 | 119 | if(fh = Open(file, MODE_OLDFILE)) { 120 | #ifdef __amigaos4__ 121 | int64 len = GetFileSize(fh); 122 | #else 123 | Seek(fh, 0, OFFSET_END); 124 | long len = Seek(fh, 0, OFFSET_BEGINNING); 125 | #endif 126 | 127 | if(len <= 0) return 0; 128 | 129 | buffer = AllocVec(len, MEMF_ANY | MEMF_PRIVATE); 130 | if(buffer == NULL) { 131 | char message[200]; 132 | sprintf(message, locale_get_string( MSG_OUTOFMEMORYSCANNINGFILE ), file); 133 | open_error_req(message, locale_get_string( MSG_OK ), awin); 134 | return -2; 135 | } 136 | 137 | Read(fh, buffer, len); 138 | Close(fh); 139 | 140 | res = xvs_scan_virus(file, buffer, len, delete, awin); 141 | FreeVec(buffer); 142 | } 143 | 144 | return res; 145 | } 146 | -------------------------------------------------------------------------------- /src/xvs.h: -------------------------------------------------------------------------------- 1 | /* Avalanche 2 | * (c) 2022 Chris Young 3 | * 4 | * This program is free software; you can redistribute it and/or modify 5 | * it under the terms of the GNU General Public License as published by 6 | * the Free Software Foundation; either version 2 of the License, or 7 | * (at your option) any later version. 8 | * 9 | * This program is distributed in the hope that it will be useful, 10 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 | * GNU General Public License for more details. 13 | */ 14 | 15 | #ifndef XVS_H 16 | #define XVS_H 1 17 | 18 | long xvs_scan(char *file, BOOL delete, void *awin); 19 | long xvs_scan_buffer(UBYTE *buf, ULONG len, void *awin); 20 | #endif 21 | --------------------------------------------------------------------------------