aboutsummaryrefslogtreecommitdiffstats
path: root/sisinstall
diff options
context:
space:
mode:
authorFritz Elfert <felfert@to.com>2002-02-28 20:56:59 +0000
committerFritz Elfert <felfert@to.com>2002-02-28 20:56:59 +0000
commiteecba3b5fcb47a01e6e13ee1940def989f6dd22d (patch)
tree970f3113de0d2b9b0544c1420117e0cf9633abcd /sisinstall
parent12241e0ff5ea242891fc3a8c177e8f55e897f2a3 (diff)
downloadplptools-eecba3b5fcb47a01e6e13ee1940def989f6dd22d.tar.gz
plptools-eecba3b5fcb47a01e6e13ee1940def989f6dd22d.tar.bz2
plptools-eecba3b5fcb47a01e6e13ee1940def989f6dd22d.zip
- Added SIS stuff by Daniel Brahneborg
Diffstat (limited to 'sisinstall')
-rw-r--r--sisinstall/.cvsignore5
-rw-r--r--sisinstall/Makefile.am11
-rw-r--r--sisinstall/psion.cpp84
-rw-r--r--sisinstall/psion.h37
-rw-r--r--sisinstall/sisinstaller.cpp203
-rw-r--r--sisinstall/sisinstaller.h30
-rw-r--r--sisinstall/sismain.cpp62
7 files changed, 432 insertions, 0 deletions
diff --git a/sisinstall/.cvsignore b/sisinstall/.cvsignore
new file mode 100644
index 0000000..cef7c58
--- /dev/null
+++ b/sisinstall/.cvsignore
@@ -0,0 +1,5 @@
+Makefile.in
+Makefile
+sisinstall
+.libs
+.deps
diff --git a/sisinstall/Makefile.am b/sisinstall/Makefile.am
new file mode 100644
index 0000000..243f877
--- /dev/null
+++ b/sisinstall/Makefile.am
@@ -0,0 +1,11 @@
+# $Id$
+#
+INCLUDES=-I$(top_srcdir)/lib
+
+bin_PROGRAMS = sisinstall
+sisinstall_LDADD = $(top_srcdir)/lib/libplp.la
+sisinstall_SOURCES = psion.cpp sisinstaller.cpp sismain.cpp
+EXTRA_DIST = psion.h sisinstaller.h
+
+maintainer-clean-local:
+ rm -f Makefile.in
diff --git a/sisinstall/psion.cpp b/sisinstall/psion.cpp
new file mode 100644
index 0000000..6aeadf1
--- /dev/null
+++ b/sisinstall/psion.cpp
@@ -0,0 +1,84 @@
+#include "psion.h"
+
+#include <plpintl.h>
+#include <rfsv.h>
+#include <rpcs.h>
+#include <rfsvfactory.h>
+#include <rpcsfactory.h>
+#include <bufferarray.h>
+#include <bufferstore.h>
+#include <ppsocket.h>
+
+#include <dirent.h>
+#include <netdb.h>
+
+#include <stdio.h>
+
+bool
+Psion::connect()
+{
+ int sockNum = DPORT;
+
+#if 0
+ setlocale (LC_ALL, "");
+ textdomain(PACKAGE);
+#endif
+
+ struct servent *se = getservbyname("psion", "tcp");
+ endservent();
+ if (se != 0L)
+ sockNum = ntohs(se->s_port);
+
+#if 0
+ // Command line parameter processing
+ if ((argc > 2) && !strcmp(argv[1], "-p")) {
+ sockNum = atoi(argv[2]);
+ argc -= 2;
+ for (int i = 1; i < argc; i++)
+ argv[i] = argv[i + 2];
+ }
+#endif
+
+ m_skt = new ppsocket();
+ if (!m_skt->connect(NULL, sockNum)) {
+ return 1;
+ }
+ m_skt2 = new ppsocket();
+ if (!m_skt2->connect(NULL, sockNum)) {
+ return 1;
+ }
+ m_rfsvFactory = new rfsvfactory(m_skt);
+ m_rpcsFactory = new rpcsfactory(m_skt2);
+ m_rfsv = m_rfsvFactory->create(true);
+ m_rpcs = m_rpcsFactory->create(true);
+ if ((m_rfsv != NULL) && (m_rpcs != NULL))
+ return true;
+}
+
+Psion::~Psion()
+{
+ disconnect();
+}
+
+Enum<rfsv::errs>
+Psion::devlist(u_int32_t& devbits)
+{
+ printf("Running devlist\n");
+ u_int32_t devb;
+ Enum<rfsv::errs> res;
+ res = m_rfsv->devlist(devb);
+ devbits = devb;
+ return res;
+}
+
+void
+Psion::disconnect()
+{
+ delete m_rfsv;
+ delete m_rpcs;
+ delete m_skt;
+ delete m_skt2;
+ delete m_rfsvFactory;
+ delete m_rpcsFactory;
+}
+
diff --git a/sisinstall/psion.h b/sisinstall/psion.h
new file mode 100644
index 0000000..0043140
--- /dev/null
+++ b/sisinstall/psion.h
@@ -0,0 +1,37 @@
+#ifndef _PSION_H
+#define _PSION_H
+
+#include <Enum.h>
+#include "rfsv.h"
+
+class ppsocket;
+class rfsvfactory;
+class rpcsfactory;
+class rpcs;
+
+class Psion
+{
+public:
+
+ virtual ~Psion();
+
+ bool connect();
+
+ Enum<rfsv::errs> devlist(u_int32_t& devbits);
+
+ void disconnect();
+
+ rfsv* m_rfsv;
+
+private:
+
+ ppsocket* m_skt;
+ ppsocket* m_skt2;
+ rfsvfactory* m_rfsvFactory;
+ rpcsfactory* m_rpcsFactory;
+ rpcs* m_rpcs;
+
+};
+
+#endif
+
diff --git a/sisinstall/sisinstaller.cpp b/sisinstall/sisinstaller.cpp
new file mode 100644
index 0000000..efd0bfe
--- /dev/null
+++ b/sisinstall/sisinstaller.cpp
@@ -0,0 +1,203 @@
+
+#include "sisinstaller.h"
+
+#include "sisfile.h"
+#include "sisfilerecord.h"
+#include "sisreqrecord.h"
+#include "psion.h"
+
+#include <unistd.h>
+#include <stdio.h>
+
+void
+SISInstaller::setPsion(Psion* psion)
+{
+ m_psion = psion;
+}
+
+void
+SISInstaller::run(SISFile* file, uchar* buf)
+{
+ run(file, buf, 0);
+}
+
+void
+SISInstaller::run(SISFile* file, uchar* buf, SISFile* parent)
+{
+ int n;
+ int lang;
+ if (parent == 0)
+ {
+ n = file->m_header.m_nlangs;
+ if (n == 1)
+ {
+ printf("You have only one language: %s\n",
+ file->getLanguage(0)->m_name);
+ lang = 0;
+ }
+ else
+ {
+ printf("Select a language (%d alternatives):\n", n);
+ for (int i = 0; i < n; ++i)
+ {
+ printf(" %d. %s\n", i, file->getLanguage(i)->m_name);
+ }
+ lang = 0;
+ }
+ }
+ else
+ {
+ lang = parent->getLanguage();
+ printf("Forcing language to %d\n", lang);
+ }
+ file->setLanguage(lang);
+ printf("Installing component: `%s'\n", file->getName());
+
+ // Check Requisites.
+ //
+ n = file->m_header.m_nreqs;
+ printf("Found %d requisites, of some sort.\n", n);
+ for (int i = 0; i < n; ++i)
+ {
+ SISReqRecord* reqRecord = &file->m_reqRecords[i];
+ printf(" Check if app with uid %08x exists with version >= %d.%d\n",
+ reqRecord->m_uid,
+ reqRecord->m_major,
+ reqRecord->m_minor);
+ }
+
+ // Check previous version.
+ //
+ printf(
+ "Checking if this app (uid %08x) exists with a version less than %d.%d.\n",
+ file->m_header.m_uid1,
+ file->m_header.m_major,
+ file->m_header.m_minor);
+
+ // Install file components.
+ //
+ n = file->m_header.m_nfiles;
+ printf("Found %d files.\n", n);
+ char drive = (parent == 0) ? 0 : parent->m_header.m_installationDrive;
+ file->m_header.m_installationFiles = 0;
+ int firstFile = -1;
+ while (n-- > 0)
+ {
+ SISFileRecord* fileRecord = &file->m_fileRecords[n];
+ int ix = 0;
+ if (fileRecord->m_flags & 1)
+ ix = lang;
+ char ch;
+#if 0
+ printf("FirstFile = %d, ptr = %d, length = %d\n",
+ firstFile,
+ fileRecord->m_filePtrs[ix],
+ fileRecord->m_fileLengths[ix]);
+#endif
+ if ((firstFile == -1) ||
+ (firstFile >= fileRecord->m_filePtrs[ix]))
+ firstFile = fileRecord->m_filePtrs[ix];
+
+// We can only do this if we search all files...
+// fileRecord->m_filePtrs[ix] + fileRecord->m_fileLengths[ix]
+
+ switch (fileRecord->m_fileType)
+ {
+ case 0:
+ if (buf[fileRecord->m_destPtr] == '!')
+ {
+ if (drive == 0)
+ {
+#if 0
+ u_int32_t devbits = 0;
+ Enum<rfsv::errs> res;
+ if ((res = m_psion->m_rfsv->devlist(devbits)) == rfsv::E_PSI_GEN_NONE)
+ {
+ for (int i = 0; i < 26; i++)
+ {
+ PlpDrive plpdrive;
+ if ((devbits & 1) != 0)
+ {
+ u_int32_t mediaType = plpdrive.getMediaType();
+ if ((mediaType == 3) || (mediaType == 5))
+ {
+ printf("%c: %d bytes free\n", 'A' + i, plpdrive.getSpace());
+ }
+ }
+ devbits >>= 1;
+ }
+ }
+#endif
+ printf("Please select a drive\n");
+ read(0, &ch, 1);
+ if (ch >= 'a' && ch <= 'z')
+ drive = ch;
+ else
+ drive = 'c';
+ }
+ file->m_header.m_installationDrive = drive;
+ }
+ printf("Copying %d bytes to %.*s\n",
+ fileRecord->m_fileLengths[ix],
+ fileRecord->m_destLength,
+ buf + fileRecord->m_destPtr);
+ break;
+ case 1:
+ printf("Info:\n%.*s\n",
+ fileRecord->m_fileLengths[ix],
+ buf + fileRecord->m_filePtrs[ix]);
+ switch (fileRecord->m_fileDetails)
+ {
+ case 0:
+ printf("Continue\n");
+// read(0, &ch, 1);
+ break;
+ case 1:
+ printf("Skip next file? Yes/No\n");
+// read(0, &ch, 1);
+ break;
+ case 2:
+ printf("[Continue installation?] Yes/No\n");
+// read(0, &ch, 1);
+ break;
+ }
+ break;
+ case 2:
+ {
+ printf("Recursive sis file...\n");
+ SISFile sisFile;
+ uchar* buf2 = buf + fileRecord->m_filePtrs[ix];
+ sisFile.fillFrom(buf2);
+ SISInstaller installer;
+ installer.run(&sisFile, buf2, file);
+ if (0 == file->m_header.m_installationDrive)
+ drive =
+ file->m_header.m_installationDrive =
+ sisFile.m_header.m_installationDrive;
+ break;
+ }
+ case 3:
+ printf("Run %.*s during installation/remove\n",
+ fileRecord->m_destLength, buf + fileRecord->m_destPtr);
+ break;
+ case 4:
+ printf("Running the app will create %.*s\n",
+ fileRecord->m_destLength, buf + fileRecord->m_destPtr);
+ break;
+ }
+
+ file->m_header.m_installationFiles++;
+ }
+ printf("Installed %d files of %d, cutting at offset %d\n",
+ file->m_header.m_installationFiles,
+ file->m_header.m_nfiles,
+ firstFile);
+
+ // Set the new shortened size somewhere.
+ //
+
+ // Copy the updated sis file to the epoc machine.
+ //
+
+}
+
diff --git a/sisinstall/sisinstaller.h b/sisinstall/sisinstaller.h
new file mode 100644
index 0000000..653ede9
--- /dev/null
+++ b/sisinstall/sisinstaller.h
@@ -0,0 +1,30 @@
+#ifndef _SISINSTALLER_H
+#define _SISINSTALLER_H
+
+#include "sistypes.h"
+
+class Psion;
+class SISFile;
+
+/**
+ * A minimal SIS installer.
+ * Handles recursive sis files.
+ */
+class SISInstaller
+{
+public:
+
+ void run(SISFile* file, uchar* buf);
+
+ void run(SISFile* file, uchar* buf, SISFile* parent);
+
+ void setPsion(Psion* psion);
+
+private:
+
+ Psion* m_psion;
+
+};
+
+#endif
+
diff --git a/sisinstall/sismain.cpp b/sisinstall/sismain.cpp
new file mode 100644
index 0000000..1b9f714
--- /dev/null
+++ b/sisinstall/sismain.cpp
@@ -0,0 +1,62 @@
+
+#include "sisfile.h"
+#include "sisinstaller.h"
+#include "psion.h"
+
+#include <errno.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+
+static void error(int line)
+{
+ fprintf(stderr, "Got errno = %d (%s) on line %d\n",
+ errno, strerror(errno), line);
+ exit(1);
+}
+
+void main(int argc, char* argv[])
+{
+ char* filename = 0;
+ if (argc > 1)
+ filename = argv[1];
+ else
+ return 0;
+ struct stat st;
+ if (-1 == stat(filename, &st))
+ error(__LINE__);
+ off_t len = st.st_size;
+ if (logLevel >= 2)
+ printf("File is %d bytes long\n", len);
+ uchar* buf = new uchar[len];
+ int fd = open(filename, O_RDONLY);
+ if (-1 == fd)
+ error(__LINE__);
+ if (-1 == read(fd, buf, len))
+ error(__LINE__);
+ close(fd);
+ Psion psion;
+#if 0
+ if (!psion.connect())
+ {
+ printf("Couldn't connect with the Psion\n");
+ exit(1);
+ }
+#endif
+ createCRCTable();
+ SISFile sisFile;
+ sisFile.fillFrom(buf);
+ SISInstaller installer;
+ installer.setPsion(&psion);
+ installer.run(&sisFile, buf);
+#if 0
+ psion.disconnect();
+#endif
+
+ exit(0);
+}
+