revert between 56095 -> 55830 in arch
[AROS.git] / arch / ppc-sam440 / parthenogenesis / parthenogenesis.c
blobaa18ec1fea2cc3eab9476e56bfc832e3933d8986
1 /*
2 * Copyright (C) 2012, The AROS Development Team
3 * All right reserved.
4 * Author: Jason S. McMullan <jason.mcmullan@gmail.com>
6 * Licensed under the AROS PUBLIC LICENSE (APL) Version 1.1
7 */
9 #include <stdio.h>
10 #include <stdlib.h>
11 #include <unistd.h>
12 #include <fcntl.h>
13 #include <dirent.h>
14 #include <string.h>
16 #include <sys/types.h>
17 #include <sys/stat.h>
19 #include <adf/adflib.h>
20 #include <adf/adf_hd.h>
22 #define SZ_1G (1UL << 30)
23 #define SZ_2G (1UL << 31)
25 static int usage(const char *program)
27 printf("Usage:\n"
28 "%s /dev/sdb /path/to/Parthnope [/path/to/AROS]\n"
29 , program);
30 return EXIT_FAILURE;
33 static void *openmem(const char *name, size_t *sizep)
35 size_t size;
36 int fd, len;
37 void *mem;
39 fd = open(name, O_RDONLY);
40 if (fd < 0)
41 return NULL;
43 size = lseek(fd, 0, SEEK_END);
44 if (size < 0)
45 return NULL;
46 lseek(fd, 0, SEEK_SET);
47 mem = malloc(size);
48 if (mem == NULL)
49 return NULL;
51 len = read(fd, mem, size);
52 if (len != size) {
53 free(mem);
54 return NULL;
57 close(fd);
59 *sizep = size;
60 return mem;
63 static int copyToVolume(struct Volume *vol, const char *path, int depth)
65 struct dirent *de;
66 DIR *dir = opendir(path);
67 char here[PATH_MAX];
68 SECTNUM acd = adfCurrentDir(vol);
69 int files = 0, rc = 0;
71 if (dir == NULL) {
72 perror(path);
73 return -1;
76 getcwd(here, sizeof(here));
77 chdir(path);
79 while (rc >= 0 && (de = readdir(dir))) {
80 struct stat st;
81 if (strcmp(de->d_name,".") == 0 ||
82 strcmp(de->d_name,"..") == 0)
83 continue;
84 if (stat(de->d_name, &st) == 0) {
85 if (S_ISDIR(st.st_mode)) {
86 printf("D %*c%s", depth * 2, ' ', de->d_name);
87 if (adfCreateDir(vol, acd, de->d_name) == RC_OK) {
88 if (adfChangeDir(vol, de->d_name) == RC_OK) {
89 printf("\n");
90 rc = copyToVolume(vol, de->d_name, depth+1);
91 if (rc >= 0)
92 files+=rc;
93 adfParentDir(vol);
94 } else {
95 printf(": Can't ChDir\n");
97 } else {
98 printf(": Can't create\n");
100 } else if (S_ISREG(st.st_mode)) {
101 int fd = open(de->d_name, O_RDONLY);
102 printf("F %*c%s\n", depth * 2, ' ', de->d_name);
103 if (fd >= 0) {
104 struct File *file = adfOpenFile(vol, de->d_name, "w");
105 if (file) {
106 char buff[256];
107 int len;
108 while ((len = read(fd, buff, 256)) > 0) {
109 adfWriteFile(file, len, buff);
111 adfCloseFile(file);
112 files++;
114 close(fd);
120 closedir(dir);
121 chdir(here);
123 return files;
126 int main(int argc, char **argv)
128 size_t size;
129 void *code;
130 struct Device *dev;
131 DIR *dir;
132 struct Partition part_boot = {
133 .volName = "DH0",
134 .volType = { 'D', 'O', 'S', 3 }, /* DOS\03 */
135 .bootable = TRUE,
137 struct Partition part_work = {
138 .volName = "DH1",
139 .volType = { 'D', 'O', 'S', 3 }, /* DOS\03 */
141 struct Partition *part[] = { &part_boot, &part_work };
143 if (argc != 3 && argc != 4) {
144 return usage(argv[0]);
147 code = openmem(argv[2], &size);
148 if (!code) {
149 perror(argv[2]);
150 return EXIT_FAILURE;
153 adfEnvInitDefault();
155 dev = adfMountDev(argv[1], FALSE);
156 if (dev && argc == 3) {
157 if (adfWriteBOOT(dev, code, size) == RC_OK) {
158 printf("SLB updated\n");
160 free(code);
161 adfUnMountDev(dev);
162 } else if (dev) {
163 ULONG lastcyl;
164 int parts = 2;
166 lastcyl = SZ_1G / 512 / dev->sectors / dev->heads;
167 if (lastcyl > dev->cylinders) {
168 lastcyl = dev->cylinders;
169 parts = 1;
171 part_boot.startCyl = 2;
172 part_boot.lenCyl = lastcyl - part_boot.startCyl;
174 part_work.startCyl = lastcyl;
175 part_work.lenCyl = dev->cylinders - lastcyl;
177 if (adfCreateHd(dev, parts, part) == RC_OK) {
178 /* Add Parthenope to the boot blocks */
179 if (adfWriteBOOT(dev, code, size) == RC_OK) {
180 struct Volume *vol;
182 if ((vol = adfMount(dev, 0, FALSE))) {
183 int files = copyToVolume(vol, argv[3], 0);
184 if (files >= 0) {
185 printf("Copied %d files\n", files);
187 adfVolumeInfo(vol);
188 adfUnMount(vol);
191 free(code);
193 adfUnMountDev(dev);
196 adfEnvCleanUp();
198 return 0;