Skip to content

Commit

Permalink
maint: Cleanup code and binaries generation and fix pam module loader (
Browse files Browse the repository at this point in the history
…#142)

Cleanup the way we generate the targets moving some stuff to scripts so
that they are more maintainable and and reusable (I'd need the proto
generation for #121 for example).

Plus address an issue we have with current module path loader when using
relative paths.
  • Loading branch information
GabrielNagy authored Dec 13, 2023
2 parents fc82613 + 191b35f commit 83cb09a
Show file tree
Hide file tree
Showing 7 changed files with 111 additions and 19 deletions.
7 changes: 5 additions & 2 deletions debian/rules
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@ export CARGO_VENDOR_DIR = vendor_rust
export DEB_HOST_GNU_TYPE DEB_HOST_RUST_TYPE
export CARGO_HOME = $(CURDIR)/debian/cargo_home

# Needed by the pam module loader
export AUTHD_PAM_MODULES_PATH = /usr/lib/$(DEB_TARGET_GNU_TYPE)/security

%:
dh $@ --buildsystem=golang --with=golang,apport

Expand Down Expand Up @@ -75,8 +78,8 @@ override_dh_auto_install:
install -Dm644 debian/pam-configs/authd debian/authd/usr/share/pam-configs/authd

# Install PAM
install -Dm644 pam/go-loader/pam_go_loader.so debian/authd/usr/lib/$(DEB_TARGET_GNU_TYPE)/security/pam_go_loader.so
install -Dm644 pam/pam_authd.so debian/authd/usr/lib/$(DEB_TARGET_GNU_TYPE)/security/pam_authd.so
install -Dm644 pam/go-loader/pam_go_loader.so debian/authd/$(AUTHD_PAM_MODULES_PATH)/pam_go_loader.so
install -Dm644 pam/pam_authd.so debian/authd/$(AUTHD_PAM_MODULES_PATH)/pam_authd.so

# Install NSS
# In Rust, HOST actually refers to the build target (see README.Debian in rustc)
Expand Down
10 changes: 4 additions & 6 deletions generate.go
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
//go:build generate

//go:generate tools/generate-proto.sh --with-grpc authd.proto

// Package authd contains the autogenerated GRPC API between the modules and daemon.
package authd

//TODO: Watch https://github.com/protocolbuffers/protobuf for any changes on the experimental status of optional fields,
// previously described on: https://github.com/protocolbuffers/protobuf/blob/main/docs/implementing_proto3_presence.md.
//
// Should it become default, remove the --experimental_allow_proto3_optional flag from the go generate command below.
//go:generate sh -c "PATH=\"$PATH:`go env GOPATH`/bin\" protoc --proto_path=. --go_out=. --go_opt=paths=source_relative --go-grpc_out=. --go-grpc_opt=paths=source_relative authd.proto --experimental_allow_proto3_optional"
5 changes: 5 additions & 0 deletions pam/generate.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
//go:build generate

//go:generate ./generate.sh -tags !pam_binary_cli

package main
27 changes: 27 additions & 0 deletions pam/generate.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
#!/usr/bin/env bash

set -euo pipefail

PROJECT_ROOT=$PWD/..
module_libname=pam_authd.so
loader_libname=pam_go_loader.so

if [ -d "$PROJECT_ROOT"/vendor ]; then
echo Vendored dependencies detected, not re-generating pam_module.go
else
go run github.com/msteinert/pam/v2/cmd/pam-moduler \
-libname "$module_libname" -type pamModule \
"${@}"
fi

cc_args=()
if [ -v AUTHD_PAM_MODULES_PATH ]; then
cc_args+=(-DAUTHD_PAM_MODULES_PATH=\""${AUTHD_PAM_MODULES_PATH}"\")
fi

${CC:-cc} -o go-loader/"$loader_libname" \
go-loader/module.c ${CFLAGS:-} -Wl,--as-needed -Wl,--allow-shlib-undefined \
-shared -fPIC -Wl,--unresolved-symbols=report-all \
-Wl,-soname,"$loader_libname" -lpam ${LDFLAGS:-} "${cc_args[@]}"

chmod 644 go-loader/"$loader_libname"
21 changes: 20 additions & 1 deletion pam/go-loader/module.c
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,15 @@
#include <stdio.h>
#include <string.h>

#ifndef AUTHD_PAM_MODULES_PATH
# if defined(__x86_64__) && defined(__gnu_linux__)
# define AUTHD_PAM_MODULES_PATH "/lib/x86_64-linux-gnu/security"
# warning No AUTHD_PAM_MODULES_PATH provided, hardcoding AUTHD_PAM_MODULES_PATH to /lib/x86_64-linux-gnu/security
# else
# error "Can't build without a AUTHD_PAM_MODULES_PATH defined"
# endif
#endif

/* When a Go shared library is loaded from C, go starts various goroutine
* (as init() at first) and if the loading code is then performing a fork
* we end up having an undefined behavior and very likely, deadlocks.
Expand Down Expand Up @@ -104,7 +113,17 @@ call_pam_function (pam_handle_t *pamh,
argc -= 1;
argv = (argc == 0) ? NULL : &argv[1];

strncpy (module_path, sub_module, PATH_MAX - 1);
if (!sub_module || *sub_module == '\0')
{
pam_error (pamh, "%s: no valid module name provided", function);
return PAM_MODULE_UNKNOWN;
}

if (*sub_module == '/')
strncpy (module_path, sub_module, PATH_MAX - 1);
else
snprintf (module_path, PATH_MAX - 1, AUTHD_PAM_MODULES_PATH "/%s", sub_module);

go_module = load_module (pamh, module_path);
if (!go_module)
{
Expand Down
10 changes: 0 additions & 10 deletions pam/pam.go
Original file line number Diff line number Diff line change
@@ -1,7 +1,3 @@
//go:generate sh -c "[ -d ../vendor ] && echo Vendored dependencies detected, not re-generating pam_module.go || go run github.com/msteinert/pam/v2/cmd/pam-moduler -libname pam_authd.so -type pamModule -tags !pam_binary_cli"
//go:generate go generate --skip="pam_module.go"
//go:generate sh -c "cc -o go-loader/pam_go_loader.so go-loader/module.c -Wl,--as-needed -Wl,--allow-shlib-undefined -shared -fPIC -Wl,--unresolved-symbols=report-all -lpam && chmod 600 go-loader/pam_go_loader.so"

// Package main is the package for the PAM library.
package main

Expand Down Expand Up @@ -37,12 +33,6 @@ const (
authenticationBrokerIDKey = "authentication-broker-id"
)

/*
FIXME: provide instructions using pam-auth-update instead!
Add to /etc/pam.d/common-auth
auth [success=3 default=die ignore=ignore] pam_authd.so
*/

func showPamMessage(mTx pam.ModuleTransaction, style pam.Style, msg string) error {
switch style {
case pam.TextInfo | pam.ErrorMsg:
Expand Down
50 changes: 50 additions & 0 deletions tools/generate-proto.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
#!/usr/bin/env bash

set -euo pipefail

# TODO: Watch https://github.com/protocolbuffers/protobuf for any changes on the
# experimental status of optional fields, previously described on:
# https://github.com/protocolbuffers/protobuf/blob/main/docs/implementing_proto3_presence.md.
args=(
--proto_path=.
--go_out=.
--go_opt=paths=source_relative

# Should it become default, remove the --experimental_allow_proto3_optional
# flag from the go generate command below.
--experimental_allow_proto3_optional
)

while [ "$#" -gt 0 ]; do
case "$1" in
--with-grpc)
args+=(
--go-grpc_out=.
--go-grpc_opt=paths=source_relative
)
shift
;;
--)
shift
break
;;
-*)
args+=("$1")
shift
;;
*)
proto_file="$1"
shift
;;
esac
done

if [ ! -e "$proto_file" ]; then
echo "No proto or invalid file provided: $proto_file"
exit 1
fi

PATH="$(go env GOPATH)/bin:$PATH"
export PATH

exec protoc "${args[@]}" "$proto_file" "${@}"

0 comments on commit 83cb09a

Please sign in to comment.