The branch main has been updated by bapt:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=a1ab15abe2e2a1ed92cbad056df71afff7e8794e

commit a1ab15abe2e2a1ed92cbad056df71afff7e8794e
Author:     Baptiste Daroussin <[email protected]>
AuthorDate: 2022-11-24 08:16:05 +0000
Commit:     Baptiste Daroussin <[email protected]>
CommitDate: 2022-11-25 07:49:58 +0000

    flua: add a chown(2) binding
    
    The main difference with the chown in luaposix, is that it checks
    and reports if a user or a group do exist when a string is passed
    as arguments
    
    Reviewed by:    kevans
    Differential Revision:  https://reviews.freebsd.org/D37479
---
 libexec/flua/modules/lposix.c | 59 +++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 59 insertions(+)

diff --git a/libexec/flua/modules/lposix.c b/libexec/flua/modules/lposix.c
index adf3a7bb9a1f..88687be2788c 100644
--- a/libexec/flua/modules/lposix.c
+++ b/libexec/flua/modules/lposix.c
@@ -30,6 +30,8 @@ __FBSDID("$FreeBSD$");
 #include <sys/stat.h>
 
 #include <errno.h>
+#include <grp.h>
+#include <pwd.h>
 #include <string.h>
 #include <unistd.h>
 
@@ -63,6 +65,62 @@ lua_chmod(lua_State *L)
        return 1;
 }
 
+static int
+lua_chown(lua_State *L)
+{
+       int n;
+       const char *path;
+       uid_t owner = (uid_t) -1;
+       gid_t group = (gid_t) -1;
+
+       n = lua_gettop(L);
+       luaL_argcheck(L, n > 1, n,
+          "chown takes at least two arguments");
+       path = luaL_checkstring(L, 1);
+       if (lua_isinteger(L, 2))
+               owner = (uid_t) lua_tointeger(L, 2);
+       else if (lua_isstring(L, 2)) {
+               struct passwd *p = getpwnam(lua_tostring(L, 2));
+               if (p != NULL)
+                       owner = p->pw_uid;
+               else
+                       return (luaL_argerror(L, 2,
+                           lua_pushfstring(L, "unknown user %s",
+                           lua_tostring(L, 2))));
+       } else if (!lua_isnoneornil(L, 2)) {
+               const char *type = luaL_typename(L, 2);
+               return (luaL_argerror(L, 2,
+                   lua_pushfstring(L, "integer or string expected, got %s",
+                   type)));
+       }
+
+       if (lua_isinteger(L, 3))
+               group = (gid_t) lua_tointeger(L, 3);
+       else if (lua_isstring(L, 3)) {
+               struct group *g = getgrnam(lua_tostring(L, 3));
+               if (g != NULL)
+                       group = g->gr_gid;
+               else
+                       return (luaL_argerror(L, 3,
+                           lua_pushfstring(L, "unknown user %s",
+                           lua_tostring(L, 3))));
+       } else if (!lua_isnoneornil(L, 3)) {
+               const char *type = luaL_typename(L, 3);
+               return (luaL_argerror(L, 3,
+                   lua_pushfstring(L, "integer or string expected, got %s",
+                   type)));
+       }
+
+       if (chown(path, owner, group) == -1) {
+               lua_pushnil(L);
+               lua_pushstring(L, strerror(errno));
+               lua_pushinteger(L, errno);
+               return (3);
+       }
+       lua_pushinteger(L, 0);
+       return (1);
+}
+
 static int
 lua_getpid(lua_State *L)
 {
@@ -82,6 +140,7 @@ static const struct luaL_Reg sys_statlib[] = {
 
 static const struct luaL_Reg unistdlib[] = {
        REG_SIMPLE(getpid),
+       REG_SIMPLE(chown),
        { NULL, NULL },
 };
 #undef REG_SIMPLE

Reply via email to