mirror of
https://git.savannah.gnu.org/git/make.git
synced 2025-01-01 01:33:51 +00:00
Formerly ar.c.~4~
This commit is contained in:
parent
3d6b586776
commit
4694e31659
1 changed files with 99 additions and 2 deletions
101
ar.c
101
ar.c
|
@ -17,10 +17,13 @@ along with GNU Make; see the file COPYING. If not, write to
|
||||||
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
|
||||||
|
|
||||||
#include "make.h"
|
#include "make.h"
|
||||||
#include "file.h"
|
|
||||||
|
|
||||||
#ifndef NO_ARCHIVES
|
#ifndef NO_ARCHIVES
|
||||||
|
|
||||||
|
#include "file.h"
|
||||||
|
#include "dep.h"
|
||||||
|
#include <fnmatch.h>
|
||||||
|
|
||||||
/* Defined in arscan.c. */
|
/* Defined in arscan.c. */
|
||||||
extern long int ar_scan ();
|
extern long int ar_scan ();
|
||||||
extern int ar_member_touch ();
|
extern int ar_member_touch ();
|
||||||
|
@ -174,5 +177,99 @@ ar_touch (name)
|
||||||
|
|
||||||
return val;
|
return val;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* State of an `ar_glob' run, passed to `ar_glob_match'. */
|
||||||
|
|
||||||
#endif
|
struct ar_glob_state
|
||||||
|
{
|
||||||
|
char *arname;
|
||||||
|
char *pattern;
|
||||||
|
unsigned int size;
|
||||||
|
struct nameseq *chain;
|
||||||
|
unsigned int n;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* This function is called by `ar_scan' to match one archive
|
||||||
|
element against the pattern in STATE. */
|
||||||
|
|
||||||
|
static long int
|
||||||
|
ar_glob_match (desc, mem, truncated,
|
||||||
|
hdrpos, datapos, size, date, uid, gid, mode,
|
||||||
|
state)
|
||||||
|
int desc;
|
||||||
|
char *mem;
|
||||||
|
int truncated;
|
||||||
|
long int hdrpos, datapos, size, date;
|
||||||
|
int uid, gid, mode;
|
||||||
|
struct ar_glob_state *state;
|
||||||
|
{
|
||||||
|
if (fnmatch (state->pattern, mem, FNM_PATHNAME|FNM_PERIOD) == 0)
|
||||||
|
{
|
||||||
|
/* We have a match. Add it to the chain. */
|
||||||
|
struct nameseq *new = (struct nameseq *) xmalloc (state->size);
|
||||||
|
new->name = concat (state->arname, mem, ")");
|
||||||
|
new->next = state->chain;
|
||||||
|
state->chain = new;
|
||||||
|
++state->n;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0L;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Alphabetic sorting function for `qsort'. */
|
||||||
|
|
||||||
|
static int
|
||||||
|
ar_glob_alphacompare (a, b)
|
||||||
|
char **a, **b;
|
||||||
|
{
|
||||||
|
return strcmp (*a, *b);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/* Glob for MEMBER_PATTERN in archive ARNAME.
|
||||||
|
Return a malloc'd chain of matching elements (or nil if none). */
|
||||||
|
|
||||||
|
struct nameseq *
|
||||||
|
ar_glob (arname, member_pattern, size)
|
||||||
|
char *arname, *member_pattern;
|
||||||
|
unsigned int size;
|
||||||
|
{
|
||||||
|
struct ar_glob_state state;
|
||||||
|
char **names;
|
||||||
|
struct nameseq *n;
|
||||||
|
unsigned int i;
|
||||||
|
|
||||||
|
/* Scan the archive for matches.
|
||||||
|
ar_glob_match will accumulate them in STATE.chain. */
|
||||||
|
i = strlen (arname);
|
||||||
|
state.arname = (char *) alloca (i + 2);
|
||||||
|
bcopy (arname, state.arname, i);
|
||||||
|
state.arname[i] = '(';
|
||||||
|
state.arname[i + 1] = '\0';
|
||||||
|
state.pattern = member_pattern;
|
||||||
|
state.size = size;
|
||||||
|
state.chain = 0;
|
||||||
|
state.n = 0;
|
||||||
|
(void) ar_scan (arname, ar_glob_match, (long int) &state);
|
||||||
|
|
||||||
|
if (state.chain == 0)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
/* Now put the names into a vector for sorting. */
|
||||||
|
names = (char **) alloca (state.n * sizeof (char *));
|
||||||
|
i = 0;
|
||||||
|
for (n = state.chain; n != 0; n = n->next)
|
||||||
|
names[i++] = n->name;
|
||||||
|
|
||||||
|
/* Sort them alphabetically. */
|
||||||
|
qsort ((char *) names, i, sizeof (*names), ar_glob_alphacompare);
|
||||||
|
|
||||||
|
/* Put them back into the chain in the sorted order. */
|
||||||
|
i = 0;
|
||||||
|
for (n = state.chain; n != 0; n = n->next)
|
||||||
|
n->name = names[i++];
|
||||||
|
|
||||||
|
return state.chain;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif /* Not NO_ARCHIVES. */
|
||||||
|
|
Loading…
Reference in a new issue