Commit Diff


commit - 2b02ed351e68831d6bd5bc93f18d563679084a51
commit + 593303ab69b5378ee73b91c655b29fcb96bdf410
blob - b56279a1bfaebe0073d471a105a7b4a45a6df6ab
blob + 9a191a4cb86e69de67b69d6be99e91a1d7e5b3a7
--- gotd/session_write.c
+++ gotd/session_write.c
@@ -232,6 +232,8 @@ request_gotsys_conf(struct gotd_imsgev *iev)
 
 	if (ftruncate(gotd_session.content_fd, 0L) == -1)
 		return got_error_from_errno("ftruncate");
+	if (lseek(gotd_session.content_fd, 0L, SEEK_SET) == -1)
+		return got_error_from_errno("lseek");
 	
 	len = sizeof(content_req) + strlen(refname) + strlen(path);
 	wbuf = imsg_create(&iev->ibuf, GOTD_IMSG_PACKFILE_GET_CONTENT,
blob - 54690cf8edce3ae4c89865d8d47309038a545def
blob + c35b39ab6d3e5f029082ca0d292d0071c61de1bc
--- gotsysd/libexec/gotsys-repo-create/gotsys-repo-create.c
+++ gotsysd/libexec/gotsys-repo-create/gotsys-repo-create.c
@@ -93,6 +93,100 @@ chmod_700_repo(const char *repo_name)
 	}
 
 	return NULL;
+}
+
+static const struct got_error *
+set_head_ref(int repos_dir_fd, const char *repo_name, const char *refname)
+{
+	const struct got_error *err = NULL;
+	char relpath[_POSIX_PATH_MAX];
+	struct got_lockfile *lf = NULL;
+	int ret, fd = -1;
+	struct stat sb;
+	char *content = NULL, *buf = NULL;
+	size_t content_len;
+	ssize_t w;
+
+	ret = snprintf(relpath, sizeof(relpath),
+	    "%s/%s", repo_name, GOT_HEAD_FILE);
+	if (ret == -1)
+		return got_error_from_errno("snprintf");
+	if ((size_t)ret >= sizeof(relpath)) {
+		return got_error_msg(GOT_ERR_NO_SPACE,
+		    "repository path too long");
+	}
+
+	ret = asprintf(&content, "ref: %s\n", refname);
+	if (ret == -1)
+		return got_error_from_errno("asprintf");
+	content_len = ret;
+
+	err = got_lockfile_lock(&lf, relpath, repos_dir_fd);
+	if (err && (err->code != GOT_ERR_ERRNO || errno != ENOENT))
+		goto done;
+	err = NULL;
+	
+	fd = openat(repos_dir_fd, relpath,
+	    O_RDWR | O_CREAT | O_NOFOLLOW | O_CLOEXEC,
+	    GOT_DEFAULT_FILE_MODE);
+	if (fd == -1) {
+		err = got_error_from_errno2("open", relpath);
+		goto done;
+	}
+
+	if (fstat(fd, &sb) == -1) {
+		err = got_error_from_errno2("stat", relpath);
+		goto done;
+	}
+
+	if (sb.st_size == content_len) {
+		ssize_t r;
+
+		buf = malloc(content_len);
+		if (buf == NULL) {
+			err = got_error_from_errno("malloc");
+			goto done;
+		}
+
+		r = read(fd, buf, content_len);
+		if (r == -1) {
+			err = got_error_from_errno2("read", relpath);
+			goto done;
+		}
+
+		if (r == content_len && memcmp(buf, content, content_len) == 0)
+			goto done; /* HEAD already has the desired content */
+	}
+
+	if (ftruncate(fd, 0L) == -1) {
+		err = got_error_from_errno2("ftruncate", relpath);
+		goto done;
+	}
+	if (lseek(fd, 0L, SEEK_SET) == -1) {
+		err = got_error_from_errno2("lseek", relpath);
+		goto done;
+	}
+
+	w = write(fd, content, content_len);
+	if (w == -1)
+		err = got_error_from_errno("write");
+	else if (w != content_len) {
+		err = got_error_fmt(GOT_ERR_IO,
+		    "wrote %zd of %zu bytes to %s", w, content_len, relpath);
+	}
+done:
+	free(content);
+	free(buf);
+	if (lf) {
+		const struct got_error *unlock_err;
+
+		unlock_err = got_lockfile_unlock(lf, repos_dir_fd);
+		if (unlock_err && err == NULL)
+			err = unlock_err;
+	}
+	if (fd != -1 && close(fd) == -1 && err == NULL)
+		err = got_error_from_errno("close");
+	return err;
 }
 
 static const struct got_error *
blob - 7996125cee248ac4fb8218d775a7a8b6a3f47ddf
blob + 67115ca0e835945a579386472c68a9561804ee5c
--- gotsysd/libexec/gotsys-write-conf/gotsys-write-conf.c
+++ gotsysd/libexec/gotsys-write-conf/gotsys-write-conf.c
@@ -333,6 +333,8 @@ write_gotd_conf(void)
 
 	if (ftruncate(gotd_conf_tmpfd, 0) == -1)
 		return got_error_from_errno("ftruncate");
+	if (lseek(gotd_conf_tmpfd, 0L, SEEK_SET) == -1)
+		return got_error_from_errno("lseek");
 
 	if (clock_gettime(CLOCK_MONOTONIC, &now) == -1)
 		return got_error_from_errno("clock_gettime");
blob - 287ba8003842bf4e78f4beda762dda10d88e453b
blob + 6ba6d58350e8b94da24107ad45bdfcec87ba08bc
--- lib/repository.c
+++ lib/repository.c
@@ -1603,8 +1603,12 @@ got_repo_cache_pack(struct got_pack **packp, struct go
 			return err;
 		if (ftruncate(repo->packs[i].basefd, 0L) == -1)
 			return got_error_from_errno("ftruncate");
+		if (lseek(repo->packs[i].basefd, 0L, SEEK_SET) == -1)
+			return got_error_from_errno("lseek");
 		if (ftruncate(repo->packs[i].accumfd, 0L) == -1)
 			return got_error_from_errno("ftruncate");
+		if (lseek(repo->packs[i].accumfd, 0L, SEEK_SET) == -1)
+			return got_error_from_errno("lseek");
 	}
 
 	if (i != 0) {