aboutsummaryrefslogtreecommitdiff
path: root/src/fetch_pwd.c
blob: e04bb3126c60fea1f349c138b5170939e7793bfe (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
/*

  pkgit - package it!

  Copyright (C) 2026 dacctal
  This program is free software: you can redistribute it and/or modify
  it under the terms of the GNU General Public License as published by
  the Free Software Foundation, either version 2 of the License, or
  (at your option) any later version.

  This program is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY; without even the implied warranty of
  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  GNU General Public License for more details.

  You should have received a copy of the GNU General Public License
  along with this program.  If not, see <https://www.gnu.org/licenses/>.

*/

#include <stdio.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <ftw.h>
#include <unistd.h>

#include "fetch_pwd.h"
#include "vars.h"

static const char *pwd_dst;

static int copy_entry(const char *fpath, const struct stat *sb, int typeflag, struct FTW *ftwbuf) {
  (void)ftwbuf;
  const char *rel = fpath;
  if (rel[0] == '.' && rel[1] == '/') rel += 2;
  if (rel[0] == '\0') return 0;

  char dst[MAX_PATH_LEN];
  snprintf(dst, sizeof(dst), "%s/%s", pwd_dst, rel);

  if (typeflag == FTW_D) {
    mkdir(dst, 0755);
  } else if (typeflag == FTW_F) {
    int src_fd = open(fpath, O_RDONLY);
    if (src_fd < 0) return -1;

    int dst_fd = open(dst, O_WRONLY | O_CREAT | O_TRUNC, sb->st_mode & 07777);
    if (dst_fd < 0) { close(src_fd); return -1; }

    char buf[8192];
    ssize_t n;
    while ((n = read(src_fd, buf, sizeof(buf))) > 0) {
      ssize_t written = 0;
    while (written < n) {
      ssize_t ret = write(dst_fd, buf + written, n - written);
      if (ret < 0) { close(src_fd); close(dst_fd); return -1; }
      written += ret;
    }
  }

  close(src_fd);
  close(dst_fd);
  }
  return 0;
}

void fetch_pwd(Pkg pkg) {
  pwd_dst = pkg.src;
  nftw(".", copy_entry, 64, FTW_PHYS);
}