# HG changeset patch
# User Kim Alvefur <zash@zash.se>
# Date 1620398878 -7200
# Node ID 30feeb4d9d0b51f968c16b205137c114e62047b9
# Parent  a09685a7b330b9adfab49e018d664245748618c5
core.certmanager: Catch error from lfs

lfs.dir() throws a hard error if there's a problem, e.g. no such
directory or permission issues. This also gets called early enough that
the main loop error protection hasn't been brought up yet, causing a
proper crash.

diff -r a09685a7b330 -r 30feeb4d9d0b core/certmanager.lua
--- a/core/certmanager.lua	Fri May 07 16:35:37 2021 +0200
+++ b/core/certmanager.lua	Fri May 07 16:47:58 2021 +0200
@@ -35,6 +35,7 @@
 local select = select;
 local now = os.time;
 local next = next;
+local pcall = pcall;
 
 local prosody = prosody;
 local pathutil = require"util.paths";
@@ -112,7 +113,16 @@
 	depth_limit = depth_limit or 3;
 	if depth_limit <= 0 then return files_by_name; end
 
-	for file in lfs.dir(dir) do
+	local ok, iter, v, i = pcall(lfs.dir, dir);
+	if not ok then
+		log("error", "Error indexing certificate directory %s: %s", dir, iter);
+		-- Return an empty index, otherwise this just triggers a nil indexing
+		-- error, plus this function would get called again.
+		-- Reloading the config after correcting the problem calls this again so
+		-- that's what should be done.
+		return {}, iter;
+	end
+	for file in iter, v, i do
 		local full = pathutil.join(dir, file);
 		if lfs.attributes(full, "mode") == "directory" then
 			if file:sub(1,1) ~= "." then