Kirjoittaja Aihe: [Ratkaistu] Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?  (Luettu 423 kertaa)

kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Elikkäs olisi hakusessa kirjasto UNZIP-toiminnolle...

Mielellään sellainen, jossa ei heti puretteisi tiedostoja levylle, vaan käsiteltäisiin mieluummin streameina tai tiedostokahvojen avulla.

Googlellahan voi niitä hakea, mutta sieltä ei välttämättä löydy sopivinta.
« Viimeksi muokattu: 16.02.24 - klo:08.33 kirjoittanut kamara »

nm

  • Käyttäjä
  • Viestejä: 16189
    • Profiili
Vs: Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #1 : 09.02.24 - klo:18.58 »
libarchive on pätevä ja tukee zipin lisäksi monia muitakin pakkausformaatteja. Tosin siihen ei taida olla hyvin ylläpidettyä C++-wrapperia, mutta C-rajapinta on muistaakseni aika suoraviivainen.

Microsoft käyttää libarchivea nykyisin Windows 11:ssä, joten ehkä tietoturvakorjauksia valuu sieltä myös avoimen koodin projektiin. https://www.techspot.com/news/100663-windows-11-extends-support-archive-formats-thanks-open.html

kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Vs: Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #2 : 09.02.24 - klo:20.20 »
Kiitoksia paljon nm.

Ei ollut aiemmin tuttu, mutta speksien mukaan näyttäisi handlaavan kaikki ne formaatit, joita uskalsin toivoa.

Enää vaan pitää opetella käyttämään kyseistä kikkaretta.

kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Vs: Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #3 : 15.02.24 - klo:14.32 »
Jaahas ...
... eipäs taitoni oikein riitä. :'(

Kyllä saan paketin ladattua, ja käännettyä C:llä, mutta en osaa tehdä vastaavaa temppua C++:lla !

Olen tässä yrittänyt muutaman kerran, mutta ei vain taidot riitä...
Latasin koodin ja ajoin käskyllä:
Koodia: [Valitse]
../libarchive-3.7.2/configure

Ja sen jälkeen ...
Koodia: [Valitse]
make
Niin ohjelma toimii, muutokset muuttavat ohjelman toimintaa.


Mutta yrittäessäni kääntää sitä g++:lla, niin menee metsään...
Koodia: [Valitse]
mkdir ../g++
cd ../g++
../libarchive-3.7.2/configure CC=g++

Koodia: [Valitse]
$ ../libarchive-3.7.2/configure CC=g++

Koodia: [Valitse]
<config.log grep error >error.log

Siis xml2-kirjasto uupuu, mutta mistä sen saa, ja miksi gpp-löytää sen, muttei g++ ?


kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Vs: Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #4 : 15.02.24 - klo:14.39 »
Siis itselleni riittäisi, että pystyisin käyttämään g++:lla archive-kirjastoa kirjastona, mutta en osaa sitäkään.  :'(


Molemmissa tapauksissa on ongelmana, etten osaa liittää xml2-kirjastoa g++:lle.
« Viimeksi muokattu: 15.02.24 - klo:14.42 kirjoittanut kamara »

nm

  • Käyttäjä
  • Viestejä: 16189
    • Profiili
Vs: Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #5 : 15.02.24 - klo:14.42 »
Mielestäni libarchivea ei tarvitse kääntää itse, ellet meinaa käyttää sitä Windowsissa. Linux-jakeluissa se on valmiiksi paketoituna ja sisältyy Ubuntussakin perusjakeluun ja kuuluu tietoturvapäivitysten piiriin.

Jos kuitenkin joka tapauksessa haluat rakentaa itse, kirjasto käännetään C-kääntäjällä, koska se on puhdasta C-koodia. Voit liittää sen omaan C++-projektiisi linkittämällä joko staattisen tai dynaamisen kirjaston lopulliseen binääriin.


Siis itselleni riittäisi, että pystyisin käyttämään g++:lla archive-kirjastoa kirjastona, mutta en osaa sitäkään.  :'(

Tee mahdollisimman yksinkertainen koeohjelma ja laita se tänne näytille, niin voidaan pohtia ja iteroida, miten se käännetään libarchivea vasten.
« Viimeksi muokattu: 15.02.24 - klo:14.44 kirjoittanut nm »

kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Vs: Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #6 : 15.02.24 - klo:17.01 »
Siis itselleni riittäisi, että pystyisin käyttämään g++:lla archive-kirjastoa kirjastona, mutta en osaa sitäkään.  :'(

Tee mahdollisimman yksinkertainen koeohjelma ja laita se tänne näytille, niin voidaan pohtia ja iteroida, miten se käännetään libarchivea vasten.

Kiitos ajatuksesta. Yleensä minä olen niin tehnytkin, mutta tällä kertaa yritin haukata liian suurta palaa kerralla, ja onnistuin kirjaston käytössä ainakin yhdessä esimerkissä.

... tosin laitoin kääntäjän asetukset aika rumasti päälle, jottei kääntäjä huutele liikoja.

kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Vs: Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #7 : 15.02.24 - klo:17.14 »
JES SEHÄN TOIMII...

hello.cpp
Koodia: [Valitse]
/*
 * This file is in the public domain.
 *
 * Feel free to use it as you wish.
 */

/*
 * This example program reads an archive from stdin (which can be in
 * any format recognized by libarchive) and writes certain entries to
 * an uncompressed ustar archive on stdout.  This is a template for
 * many kinds of archive manipulation: converting formats, resetting
 * ownership, inserting entries, removing entries, etc.
 *
 *
 * sudo apt install libbz2-dev
 * To compile:
 * gcc -Wall -o tarfilter tarfilter.c -larchive -lz -lbz2
 */

#include <archive.h>
#include <archive_entry.h>
#include <iostream>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>

static void
die(const char *fmt)
{
fprintf(stderr, "%s\n",fmt);
exit(1);
}


int
main(int argc, char **argv)
{
char buff[8192];
ssize_t len;
int r;
mode_t m;
struct archive *ina;
struct archive *outa;
struct archive_entry *entry;




ina=NULL;
/*if(ina==NULL) {
std::cout << "ina=NULL\n";
}*/

/* Read an archive from stdin, with automatic format detection. */
ina = archive_read_new();
if (ina == NULL)
die("Couldn't create archive reader.");
if (archive_read_support_filter_all(ina) != ARCHIVE_OK)
die("Couldn't enable decompression");
if (archive_read_support_format_all(ina) != ARCHIVE_OK)
die("Couldn't enable read formats");
if (archive_read_open_fd(ina, 0, 10240) != ARCHIVE_OK)
die("Couldn't open input archive");

/* Write an uncompressed ustar archive to stdout. */
outa = archive_write_new();
if (outa == NULL)
die("Couldn't create archive writer.");
if (archive_write_set_compression_none(outa) != ARCHIVE_OK)
die("Couldn't enable compression");
if (archive_write_set_format_ustar(outa) != ARCHIVE_OK)
die("Couldn't set output format");
if (archive_write_open_fd(outa, 1) != ARCHIVE_OK)
die("Couldn't open output archive");


/* Examine each entry in the input archive. */
while ((r = archive_read_next_header(ina, &entry)) == ARCHIVE_OK) {
fprintf(stderr, "%s: ", archive_entry_pathname(entry));

/* Skip anything that isn't a regular file. */
if (!S_ISREG(archive_entry_mode(entry))) {
fprintf(stderr, "skipped\n");
continue;
}

/* Make everything owned by root/wheel. */
archive_entry_set_uid(entry, 0);
archive_entry_set_uname(entry, "root");
archive_entry_set_gid(entry, 0);
archive_entry_set_gname(entry, "wheel");

/* Make everything permission 0744, strip SUID, etc. */
m = archive_entry_mode(entry);
archive_entry_set_mode(entry, (m & ~07777) | 0744);

/* Copy input entries to output archive. */
if (archive_write_header(outa, entry) != ARCHIVE_OK)
die("Error writing output archive");
if (archive_entry_size(entry) > 0) {
len = archive_read_data(ina, buff, sizeof(buff));
while (len > 0) {
if (archive_write_data(outa, buff, len) != len)
die("Error writing output archive");
len = archive_read_data(ina, buff, sizeof(buff));
}
if (len < 0)
die("Error reading input archive");
}
fprintf(stderr, "copied\n");
}


if (r != ARCHIVE_EOF)
die("Error reading archive");
/* Close the archives.  */
if (archive_read_free(ina) != ARCHIVE_OK)
die("Error closing input archive");
if (archive_write_free(outa) != ARCHIVE_OK)
die("Error closing output archive");


return (0);
}

Koodia: [Valitse]
g++ -Wno-deprecated-declarations -o hello hello.cpp -larchive -lz -lbz2

Vielä pitää tehdä unzip:n purun jälkeinen käsittely.

Edit - Tämäkin toiminallisuus nippa nappa riittää, mutta yritetään parantaa...
« Viimeksi muokattu: 15.02.24 - klo:17.16 kirjoittanut kamara »

kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Vs: [Ratkaistu] Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #8 : 16.02.24 - klo:08.38 »
JES sainhan sen unzip:nkin toimimaan g++:lla !!!

Kiitoksia paljon nm.

Ratkaisu ei ollut kovinkaan kaunis, mutta kuitenkin itselleni on pääasia, että yleensäkin kääntyy G++:lla.

Käännös käsky:
Koodia: [Valitse]
g++ "-DBSDUNZIP_VERSION_STRING=\"Kamaran beta versio\"" -DHAVE_FNMATCH_H -DHAVE_UNISTD_H -DHAVE_FNMATCH -DHAVE_STDLIB_H -DHAVE_STDARG_H -DHAVE_STRING_H -Wno-deprecated-declarations -o unzip/bsdunzip unzip/bsdunzip.h unzip/bsdunzip.cpp unzip/err.h unzip/err.cpp unzip/lafe_platform.h unzip/passphrase.h unzip/passphrase.cpp unzip/cmdline.cpp -larchive -lz

kamara

  • Käyttäjä
  • Viestejä: 2938
    • Profiili
Vs: [Ratkaistu] Mikä olisi hyvä kirjasto unzip:ksi C++:lle ?
« Vastaus #9 : 16.02.24 - klo:08.47 »
Tässä tärkein diffi, joka ei tosin ole kaikkien diffien äiti...
Koodia: [Valitse]
--- ../../Lataukset/pakkausOhjelmanSorsat/libarchive-3.7.2/unzip/bsdunzip.c 2024-02-15 17:35:04.877180993 +0200
+++ bsdunzip.cpp 2024-02-16 08:27:51.112305013 +0200
@@ -3,6 +3,7 @@
  *
  * Copyright (c) 2009, 2010 Joerg Sonnenberger <joerg@NetBSD.org>
  * Copyright (c) 2007-2008 Dag-Erling Smørgrav
+ * Copyright (c) 2024 Kamara
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -29,15 +30,20 @@
  *
  * $FreeBSD$
  *
+ * Kääntyy ...
+ * g++ "-DBSDUNZIP_VERSION_STRING=\"Kamaran beta versio\"" -DHAVE_FNMATCH_H -DHAVE_UNISTD_H -DHAVE_FNMATCH -DHAVE_STDLIB_H -DHAVE_STDARG_H -DHAVE_STRING_H -Wno-deprecated-declarations -o unzip/bsdunzip unzip/bsdunzip.h unzip/bsdunzip.cpp unzip/err.h unzip/err.cpp unzip/lafe_platform.h unzip/passphrase.h unzip/passphrase.cpp unzip/cmdline.cpp -larchive -lz
+ *
+ *
+ *
  * This file would be much shorter if we didn't care about command-line
  * compatibility with Info-ZIP's UnZip, which requires us to duplicate
  * parts of libarchive in order to gain more detailed control of its
  * behaviour for the purpose of implementing the -n, -o, -L and -a
  * options.
  */
-
+#include <iostream>
 #include "bsdunzip_platform.h"
-
+#include "passphrase.h"
 #ifdef HAVE_SYS_QUEUE_H
 #include <sys/queue.h>
 #else
@@ -78,11 +84,12 @@
 #include <sys/time.h>
 #endif
 #endif
-
+#include <fcntl.h>
 #include "bsdunzip.h"
 #include "passphrase.h"
 #include "err.h"
-
+//#include "cmdline.cpp"
+//#include <fnmatch.h>
 // Oma lisäys arvonta
 //extern "C" void lafe_setprogname(char const*,char const*);
 // Oma lisäys arvonta loppuu...
@@ -121,7 +128,6 @@ static int tty;
 static int unzip_exclude_mode = 0;
 
 int bsdunzip_optind;
-
 /* convenience macro */
 /* XXX should differentiate between ARCHIVE_{WARN,FAIL,RETRY} */
 #define ac(call) \
@@ -158,6 +164,8 @@ error(const char *fmt, ...)
  exit(EXIT_FAILURE);
 }
 
+
+
 /* fatal error message, no errno */
 static void
 errorx(const char *fmt, ...)
@@ -212,7 +220,6 @@ static void
 info(const char *fmt, ...)
 {
  va_list ap;
-
  if (q_opt && !unzip_debug)
  return;
  va_start(ap, fmt);
@@ -225,7 +232,6 @@ info(const char *fmt, ...)
  else
  noeol = fmt[strlen(fmt) - 1] != '\n';
 }
-
 /* debug message (if unzip_debug) */
 static void
 debug(const char *fmt, ...)
@@ -244,7 +250,6 @@ debug(const char *fmt, ...)
  else
  noeol = fmt[strlen(fmt) - 1] != '\n';
 }
-
 /* duplicate a path name, possibly converting to lower case */
 static char *
 pathdup(const char *path)
@@ -852,6 +857,8 @@ extract(struct archive *a, struct archiv
  free(pathname);
 }
 
+// Rivi 854  20240216
+
 static void
 extract_stdout(struct archive *a, struct archive_entry *e)
 {
@@ -894,7 +901,6 @@ extract_stdout(struct archive *a, struct
 
  free(pathname);
 }
-
 /*
  * Print the name of an entry to stdout.
  */
@@ -960,7 +966,6 @@ test(struct archive *a, struct archive_e
 
  return error_count;
 }
-
 /*
  * Callback function for reading passphrase.
  * Originally from cpio.c and passphrase.c, libarchive.
@@ -991,6 +996,7 @@ passphrase_callback(struct archive *a, v
  return p;
 }
 
+
 /*
  * Main loop: open the zipfile, iterate over its contents and decide what
  * to do with each entry.
@@ -1107,6 +1113,7 @@ version(void)
         exit(0);
 }
 
+
 static int
 getopts(int argc, char *argv[])
 {
@@ -1205,6 +1212,9 @@ getopts(int argc, char *argv[])
  return (bsdunzip_optind);
 }
 
+
+/* command-line options */
+
 int
 main(int argc, char *argv[])
 {
@@ -1212,7 +1222,7 @@ main(int argc, char *argv[])
  int nopts;
 
  lafe_setprogname(*argv, "bsdunzip");
-
+ std::cout << "C++ toimii myös!!!\n";
  if (isatty(STDOUT_FILENO))
  tty = 1;
 
@@ -1283,5 +1293,5 @@ main(int argc, char *argv[])
 
  unzip(zipfile);
 
- exit(EXIT_SUCCESS);
+ exit(0);
 }

« Viimeksi muokattu: 16.02.24 - klo:09.06 kirjoittanut kamara »