--- Begin Message ---
Package: reprepro
Version: 3.5.0
Tags: patch
This bug is not about the Debian packaging of reprepro, but about
compiling the upstream source on a non-Linux system.
For various reasons, I'm compiling reprepro for AIX 5.3 with GCC, to
use on IBM i5/OS V5R4 for a few hundred Debian PCs. I encountered a
handful of problems that needed changes, as listed below, and I'm
including a patch for most of them. Overall I'm very impressed with
the portability of the code.
- A number of the files use malloc() and free() without including
<stdlib.h>. The AIX C library is careful only to define these where
the various standards say they should be found. I haven't provided a
patch for this one.
- The last parameter for execl() should be (char*)NULL, not just NULL,
in case char* is a different size to whatever NULL resolves to. GCC
4.3 warns about this on AIX.
- AIX 5.3 doesn't provide O_NOFOLLOW. I most cases, this is combined
with O_EXCL which seems to be redundant, and I've removed it; in
donefile.c I've taken the potential security exposure and not used it.
You might wish to define it to 0 instead.
- AIX 5.3 doesn't have <endian.h>, but does get the BSD-ish
BYTE_ORDER, BIG_ENDIAN and LITTLE_ENDIAN macros if you include
<sys/param.h> and/or <sys/types.h>. I haven't included a patch for
configure.ac, etc., to get them to detect HAVE_ENDIAN_H on Linux, but
it should be trivial. Alternatively, there's AC_C_BIGENDIAN.
- AIX 5.3 doesn't have vasnprintf (or dprintf). I've removed
vmprintf(), changed formaterror to use snprintf with a static buffer
that is much larger than anything it will have to hold, and changed
mprintf() and dprintf() to call vsnprintf twice, as shown in the GNU
libc manual. I figure that there's no point making dprintf() use
vasprintf(), because they're both GNU libc extensions.
- _D_EXACT_NAMELEN is a GNU extension. I just use strlen(r->d_name) if
it isn't defined.
- I don't check zlibCompileFlags() when using zlib 1.1, which is what
I have available.
- AIX doesn't have getopt_long, but I've compiled against libiberty from GCC.
- AIX GCC needs an option "-pthread" to compile and link threadsafe
code (like Berkeley DB), not -D_REENTRANT. I added this option to the
CFLAGS when running configure. I don't know how autoconf is supposed
to discover this.
Please let me know if you'd like any more information.
--
Laissez lire, et laissez danser; ces deux amusements ne feront jamais
de mal au monde.
*** aptmethod.c.orig Fri Jun 6 21:07:53 2008
--- aptmethod.c Tue Jun 10 11:40:10 2008
***************
*** 335,341 ****
if( methodname == NULL )
exit(255);
! (void)execl(methodname,methodname,NULL);
e = errno;
fprintf(stderr, "Error %d while executing '%s': %s\n",
--- 335,341 ----
if( methodname == NULL )
exit(255);
! (void)execl(methodname,methodname,(char*)NULL);
e = errno;
fprintf(stderr, "Error %d while executing '%s': %s\n",
*** checks.c.orig Wed Apr 9 01:01:42 2008
--- checks.c Tue Jun 10 10:34:11 2008
***************
*** 171,185 ****
static const char *formaterror(const char *format, ...) {
va_list ap;
! static char *data = NULL;
- if( data != NULL )
- free(data);
va_start(ap, format);
! data = vmprintf(format, ap);
va_end(ap);
- if( data == NULL )
- return "Out of memory";
return data;
}
--- 171,181 ----
static const char *formaterror(const char *format, ...) {
va_list ap;
! static char data[1024];
va_start(ap, format);
! snprintf(data, sizeof(data), format, ap);
va_end(ap);
return data;
}
*** database.c.orig Wed Apr 9 01:01:43 2008
--- database.c Tue Jun 10 11:28:38 2008
***************
*** 84,90 ****
lockfile = calc_dirconcat(db->directory, "lockfile");
if( lockfile == NULL )
return RET_ERROR_OOM;
! fd =
open(lockfile,O_WRONLY|O_CREAT|O_EXCL|O_NOFOLLOW|O_NOCTTY,S_IRUSR|S_IWUSR);
while( fd < 0 ) {
int e = errno;
if( e == EEXIST ) {
--- 84,90 ----
lockfile = calc_dirconcat(db->directory, "lockfile");
if( lockfile == NULL )
return RET_ERROR_OOM;
! fd = open(lockfile,O_WRONLY|O_CREAT|O_EXCL|O_NOCTTY,S_IRUSR|S_IWUSR);
while( fd < 0 ) {
int e = errno;
if( e == EEXIST ) {
***************
*** 95,101 ****
while( timetosleep > 0 )
timetosleep = sleep(timetosleep);
tries++;
! fd =
open(lockfile,O_WRONLY|O_CREAT|O_EXCL|O_NOFOLLOW|O_NOCTTY,S_IRUSR|S_IWUSR);
continue;
}
--- 95,101 ----
while( timetosleep > 0 )
timetosleep = sleep(timetosleep);
tries++;
! fd =
open(lockfile,O_WRONLY|O_CREAT|O_EXCL|O_NOCTTY,S_IRUSR|S_IWUSR);
continue;
}
*** donefile.c.orig Mon Mar 3 04:37:39 2008
--- donefile.c Tue Jun 10 11:43:20 2008
***************
*** 36,42 ****
--- 36,46 ----
char *donefilename = calc_addsuffix(filename,"done");
if( donefilename == NULL )
return RET_ERROR_OOM;
+ #ifdef O_NOFOLLOW
fd = open(donefilename, O_RDONLY|O_NOCTTY|O_NOFOLLOW, 0666);
+ #else
+ fd = open(donefilename, O_RDONLY|O_NOCTTY, 0666);
+ #endif
if( fd < 0 ) {
int e = errno;
if( e == EACCES || e == ENOENT ) {
***************
*** 98,105 ****
--- 102,113 ----
return RET_ERROR_OOM;
md5sum = checksums_getmd5sum(checksums);
+ #ifdef O_NOFOLLOW
fd = open(donefilename, O_WRONLY|O_CREAT|O_TRUNC|O_NOCTTY|O_NOFOLLOW,
0666);
+ #else
+ fd = open(donefilename, O_WRONLY|O_CREAT|O_TRUNC|O_NOCTTY, 0666);
+ #endif
if( fd < 0 ) {
int e = errno;
fprintf(stderr, "Error creating file %s: %d=%s\n",
*** exports.c.orig Fri Jun 6 21:07:53 2008
--- exports.c Tue Jun 10 11:40:42 2008
***************
*** 298,304 ****
exit(255);
}
(void)execl(hook, hook, release_dirofdist(release),
! reltmpfilename, relfilename, mode, NULL);
e = errno;
fprintf(stderr, "Error %d while executing '%s': %s\n",
e, hook, strerror(e));
--- 298,304 ----
exit(255);
}
(void)execl(hook, hook, release_dirofdist(release),
! reltmpfilename, relfilename, mode, (char*)NULL);
e = errno;
fprintf(stderr, "Error %d while executing '%s': %s\n",
e, hook, strerror(e));
*** md5.c.orig Sun Jul 29 04:21:31 2007
--- md5.c Tue Jun 10 11:26:56 2008
***************
*** 28,35 ****
--- 28,38 ----
#include <config.h>
+ #ifdef HAVE_ENDIAN_H
#include <endian.h> /* for __BYTE_ORDER */
+ #endif
#include <string.h> /* for memcpy() */
+ #include <sys/param.h>
#include <sys/types.h> /* for stupid systems */
#include <netinet/in.h> /* for ntohl() */
***************
*** 37,43 ****
static void
MD5Transform(UWORD32 buf[4], UWORD32 const in[16]);
! #if __BYTE_ORDER == __BIG_ENDIAN
static void
byteSwap(UWORD32 *buf, unsigned words)
{
--- 40,47 ----
static void
MD5Transform(UWORD32 buf[4], UWORD32 const in[16]);
! #if (defined(__BYTE_ORDER) && __BYTE_ORDER == __BIG_ENDIAN) \
! || (defined(BYTE_ORDER) && BYTE_ORDER == BIG_ENDIAN)
static void
byteSwap(UWORD32 *buf, unsigned words)
{
***************
*** 50,56 ****
} while (--words);
}
#else
! #if __BYTE_ORDER == __LITTLE_ENDIAN
#define byteSwap(buf,words)
#else
#error "only supporting little or big endian currently"
--- 54,61 ----
} while (--words);
}
#else
! #if (defined(__BYTE_ORDER) && __BYTE_ORDER == __LITTLE_ENDIAN) \
! || (defined(BYTE_ORDER) && BYTE_ORDER == LITTLE_ENDIAN)
#define byteSwap(buf,words)
#else
#error "only supporting little or big endian currently"
*** mprintf.c.orig Tue Feb 5 07:56:37 2008
--- mprintf.c Tue Jun 10 12:08:48 2008
***************
*** 9,17 ****
#include "mprintf.h"
! // TODO: check for asprintf in configure and
! // write a replacement for such situations.
char * mprintf(const char *fmt,...) {
char *p;
int r;
--- 9,17 ----
#include "mprintf.h"
! #define MPRINTF_INITIAL_SIZE 256
+ #ifdef HAVE_VASPRINTF
char * mprintf(const char *fmt,...) {
char *p;
int r;
***************
*** 26,43 ****
else
return p;
}
!
! char * vmprintf(const char *fmt,va_list va) {
char *p;
int r;
! r = vasprintf(&p,fmt,va);
! /* return NULL both when r is < 0 and when NULL was returned */
! if( r < 0 )
return NULL;
! else
return p;
}
#ifndef HAVE_DPRINTF
int dprintf(int fd, const char *format, ...){
--- 26,68 ----
else
return p;
}
! #else
! char * mprintf(const char *fmt, ...) {
char *p;
int r;
+ va_list va;
! p = malloc(MPRINTF_INITIAL_SIZE);
! if ( p == NULL ) {
! r = -1;
! } else {
! va_start(va,fmt);
! r = vsnprintf(p,MPRINTF_INITIAL_SIZE,fmt,va);
! va_end(va);
! }
!
! if ( r >= MPRINTF_INITIAL_SIZE ) {
! char *newp;
! newp = realloc(p,r+1);
! if ( newp == NULL ) {
! r = -1;
! } else {
! p = newp;
! va_start(va,fmt);
! r = vsnprintf(p,r+1,fmt,va);
! va_end(va);
! }
! }
!
! /* return NULL when r < 0 */
! if ( r < 0 ) {
! free(p);
return NULL;
! } else {
return p;
+ }
}
+ #endif
#ifndef HAVE_DPRINTF
int dprintf(int fd, const char *format, ...){
***************
*** 46,54 ****
va_list va;
! va_start(va, format);
! buffer = vmprintf(format, va);
! va_end(va);
if( buffer == NULL )
return -1;
ret = write(fd, buffer, strlen(buffer));
--- 71,98 ----
va_list va;
! buffer = malloc(MPRINTF_INITIAL_SIZE);
! if ( buffer == NULL ) {
! ret = -1;
! } else {
! va_start(va,format);
! ret = vsnprintf(buffer,MPRINTF_INITIAL_SIZE,format,va);
! va_end(va);
! }
!
! if ( ret >= MPRINTF_INITIAL_SIZE ) {
! char *newp;
! newp = realloc(buffer,ret+1);
! if ( newp == NULL ) {
! ret = -1;
! } else {
! buffer = newp;
! va_start(va,format);
! ret = vsnprintf(buffer,ret+1,format,va);
! va_end(va);
! }
! }
!
if( buffer == NULL )
return -1;
ret = write(fd, buffer, strlen(buffer));
*** release.c.orig Fri Jun 6 21:07:53 2008
--- release.c Tue Jun 10 11:59:48 2008
***************
*** 481,490 ****
--- 481,492 ----
static retvalue initgzcompression(struct filetorelease *f) {
int zret;
+ #ifdef ZLIB_VERNUM
if( (zlibCompileFlags() & (1<<17)) !=0 ) {
fprintf(stderr,"libz compiled without .gz supporting code\n");
return RET_ERROR;
}
+ #endif
f->gzoutputbuffer = malloc(GZBUFSIZE);
if( f->gzoutputbuffer == NULL )
return RET_ERROR_OOM;
*** sha1.c.orig Wed Nov 21 00:58:47 2007
--- sha1.c Tue Jun 10 11:21:03 2008
***************
*** 49,61 ****
--- 49,71 ----
#include "config.h"
#endif
+ #ifdef HAVE_ENDIAN_H
#include <endian.h>
+ #endif
#include <stdint.h>
#include <stdio.h>
#include <string.h>
#include <assert.h>
+ #include <sys/param.h>
+ #include <sys/types.h>
#include "sha1.h"
+
+ #ifndef __BYTE_ORDER
+ #define __BYTE_ORDER BYTE_ORDER
+ #define __LITTLE_ENDIAN LITTLE_ENDIAN
+ #define __BIG_ENDIAN BIG_ENDIAN
+ #endif
static void SHA1_Transform(uint32_t state[5], const uint8_t buffer[64]);
*** sha256.c.orig Sat May 17 23:04:00 2008
--- sha256.c Tue Jun 10 11:24:12 2008
***************
*** 6,12 ****
--- 6,14 ----
#include <config.h>
+ #ifdef HAVE_ENDIAN_H
#include <endian.h>
+ #endif
#include <limits.h>
#include <stdint.h>
#include <stdio.h>
***************
*** 17,23 ****
#include "sha256.h"
! #if __BYTE_ORDER == __LITTLE_ENDIAN
# define SWAP(n) \
(((n) << 24) | (((n) & 0xff00) << 8) | (((n) >> 8) & 0xff00) | ((n) >>
24))
#else
--- 19,26 ----
#include "sha256.h"
! #if (defined(__BYTE_ORDER) && __BYTE_ORDER == __LITTLE_ENDIAN) \
! || (defined(BYTE_ORDER) && BYTE_ORDER == LITTLE_ENDIAN)
# define SWAP(n) \
(((n) << 24) | (((n) & 0xff00) << 8) | (((n) >> 8) & 0xff00) | ((n) >>
24))
#else
*** signature.c.orig Wed Apr 9 01:01:43 2008
--- signature.c Tue Jun 10 11:37:25 2008
***************
*** 414,420 ****
if( signature_data == NULL ) {
return RET_ERROR_OOM;
}
! fd = open(signaturename,
O_WRONLY|O_CREAT|O_EXCL|O_NOCTTY|O_NOFOLLOW, 0666);
if( fd < 0 ) {
free(signature_data);
return RET_ERRNO(errno);
--- 414,420 ----
if( signature_data == NULL ) {
return RET_ERROR_OOM;
}
! fd = open(signaturename, O_WRONLY|O_CREAT|O_EXCL|O_NOCTTY,
0666);
if( fd < 0 ) {
free(signature_data);
return RET_ERRNO(errno);
*** updates.c.orig Wed Apr 9 01:01:43 2008
--- updates.c Tue Jun 10 11:36:45 2008
***************
*** 882,888 ****
--- 882,892 ----
e, listdir, strerror(e));
return RET_ERRNO(e);
}
+ #ifdef _D_EXACT_NAMELEN
namelen = _D_EXACT_NAMLEN(r);
+ #else
+ namelen = strlen(r->d_name);
+ #endif
if( namelen < patternlen ||
strncmp(pattern,r->d_name,patternlen) != 0)
continue;
if( foundinorigins(origins,nameoffset,r->d_name) )
***************
*** 1246,1252 ****
if( f == 0 ) {
int e;
(void)closefrom(3);
! execl(listhook,listhook,index->filename,newfilename,NULL);
e = errno;
fprintf(stderr, "Error %d while executing '%s': %s\n",
e, listhook, strerror(e));
--- 1250,1256 ----
if( f == 0 ) {
int e;
(void)closefrom(3);
!
execl(listhook,listhook,index->filename,newfilename,(char*)NULL);
e = errno;
fprintf(stderr, "Error %d while executing '%s': %s\n",
e, listhook, strerror(e));
--- End Message ---