diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index f5988c94..b4af7a34 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -24,7 +24,7 @@ jobs: steps: - name: Checkout code - uses: actions/checkout@v3.2.0 + uses: actions/checkout@v3.3.0 - name: "Calculate required variables" id: variables @@ -88,7 +88,7 @@ jobs: steps: - name: Checkout code - uses: actions/checkout@v3.2.0 + uses: actions/checkout@v3.3.0 - name: "Fix ownership of repository" run: chown -R root . @@ -119,7 +119,7 @@ jobs: - name: Store binary artifacts for deployoment if: github.event_name != 'pull_request' - uses: actions/upload-artifact@v3.1.1 + uses: actions/upload-artifact@v3.1.2 with: name: tmp-storage path: '${{ matrix.bin_name }}*' @@ -142,10 +142,10 @@ jobs: steps: - name: Checkout code - uses: actions/checkout@v3.2.0 + uses: actions/checkout@v3.3.0 - name: Get Binaries and documentation built in previous jobs - uses: actions/download-artifact@v3.0.1 + uses: actions/download-artifact@v3.0.2 id: download with: name: tmp-storage @@ -172,6 +172,7 @@ jobs: working-directory: ${{steps.download.outputs.download-path}} - name: Transfer Builds to Pi-hole server for pihole checkout + if: github.actor != 'dependabot[bot]' env: USER: ${{ secrets.SSH_USER }} HOST: ${{ secrets.SSH_HOST }} diff --git a/.github/workflows/codespell.yml b/.github/workflows/codespell.yml index 49a30797..7b0553a6 100644 --- a/.github/workflows/codespell.yml +++ b/.github/workflows/codespell.yml @@ -10,7 +10,7 @@ jobs: steps: - name: Checkout repository - uses: actions/checkout@v3.2.0 + uses: actions/checkout@v3.3.0 - name: Spell-Checking uses: codespell-project/actions-codespell@master diff --git a/.github/workflows/sync-back-to-dev.yml b/.github/workflows/sync-back-to-dev.yml index 889f9622..89b6323f 100644 --- a/.github/workflows/sync-back-to-dev.yml +++ b/.github/workflows/sync-back-to-dev.yml @@ -11,7 +11,7 @@ jobs: name: Syncing branches steps: - name: Checkout - uses: actions/checkout@v3.2.0 + uses: actions/checkout@v3.3.0 - name: Opening pull request run: gh pr create -B development -H master --title 'Sync master back into development' --body 'Created by Github action' --label 'internal' env: diff --git a/src/api/docs/CMakeLists.txt b/src/api/docs/CMakeLists.txt index 6df7fbf7..65c6b91c 100644 --- a/src/api/docs/CMakeLists.txt +++ b/src/api/docs/CMakeLists.txt @@ -31,6 +31,8 @@ set(sources hex/specs/queries.yaml hex/specs/stats.yaml hex/specs/version.yaml + hex/specs/config.yaml + hex/specs/network.yaml docs.c ) diff --git a/src/api/docs/content/specs/config.yaml b/src/api/docs/content/specs/config.yaml index 62fe51f6..a1bea6ed 100644 --- a/src/api/docs/content/specs/config.yaml +++ b/src/api/docs/content/specs/config.yaml @@ -9,6 +9,8 @@ components: operationId: "get_config" description: | This API hook returns infos about the config of your Pi-hole. + parameters: + - $ref: 'config.yaml#/components/parameters/detailed' responses: '200': description: OK @@ -16,6 +18,9 @@ components: application/json: schema: $ref: 'config.yaml#/components/schemas/config' + examples: + config: + $ref: 'config.yaml#/components/examples/config' '401': description: Unauthorized content: @@ -240,101 +245,113 @@ components: type: boolean examples: config: - config: - dns: - CNAMEdeepInspect: true - blockESNI: true - EDNS0ECS: true - ignoreLocalhost: false - showDNSSEC: true - analyzeAAAA: true - analyzeOnlyAandAAAA: false - piholePTR: PI.HOLE - replyWhenBusy: ALLOW - blockTTL: 2 - blockingmode: 'NULL' - specialDomains: - mozillaCanary: true - iCloudPrivateRelay: true - reply: - host: - overwrite_v4: false - overwrite_v6: false - IPv4: 0.0.0.0 - IPv6: "::" - blocking: - overwrite_v4: false - overwrite_v6: false - IPv4: 0.0.0.0 - IPv6: "::" - rateLimit: - count: 0 - interval: 0 - port: 53 - resolver: - resolveIPv4: true - resolveIPv6: true - networkNames: true - refreshNames: IPV4_ONLY - database: - DBimport: true - DBexport: true - maxHistory: 86400 - maxDBdays: 365 - DBinterval: 60 - network: - parseARPcache: true - expire: 365 - http: - localAPIauth: false - prettyJSON: false - sessionTimeout: 300 - domain: pi.hole - acl: "+0.0.0.0/0" - port: 8080,[::]:8080 - paths: - webroot: "/var/www/html" - webhome: "/admin/" - files: - log: "/var/log/pihole/FTL.log" - pid: "/run/pihole-FTL.pid" - database: "/etc/pihole/pihole-FTL.db" - gravity: "/etc/pihole/gravity.db" - macvendor: "/etc/pihole/macvendor.db" - setupVars: "/etc/pihole/setupVars.conf" - http_info: "/var/log/pihole/HTTP_info.log" - ph7_error: "/var/log/pihole/PH7.log" - misc: - nice: -10 - delay_startup: 10 - addr2line: true - privacylevel: 0 - check: - load: true - shmem: 90 - disk: 90 - debug: - database: false - networking: false - locks: false - queries: false - flags: false - shmem: false - gc: false - arp: false - regex: false - api: false - overtime: false - status: false - caps: false - dnssec: false - vectors: false - resolver: false - edns0: false - clients: false - aliasclients: false - events: false - helper: false - config: false - extra: false - reserved: false + summary: FTL's configuration + value: + config: + dns: + CNAMEdeepInspect: true + blockESNI: true + EDNS0ECS: true + ignoreLocalhost: false + showDNSSEC: true + analyzeAAAA: true + analyzeOnlyAandAAAA: false + piholePTR: PI.HOLE + replyWhenBusy: ALLOW + blockTTL: 2 + blockingmode: 'NULL' + specialDomains: + mozillaCanary: true + iCloudPrivateRelay: true + reply: + host: + overwrite_v4: false + overwrite_v6: false + IPv4: 0.0.0.0 + IPv6: "::" + blocking: + overwrite_v4: false + overwrite_v6: false + IPv4: 0.0.0.0 + IPv6: "::" + rateLimit: + count: 0 + interval: 0 + port: 53 + resolver: + resolveIPv4: true + resolveIPv6: true + networkNames: true + refreshNames: IPV4_ONLY + database: + DBimport: true + DBexport: true + maxHistory: 86400 + maxDBdays: 365 + DBinterval: 60 + network: + parseARPcache: true + expire: 365 + http: + localAPIauth: false + prettyJSON: false + sessionTimeout: 300 + domain: pi.hole + acl: "+0.0.0.0/0" + port: 8080,[::]:8080 + paths: + webroot: "/var/www/html" + webhome: "/admin/" + files: + log: "/var/log/pihole/FTL.log" + pid: "/run/pihole-FTL.pid" + database: "/etc/pihole/pihole-FTL.db" + gravity: "/etc/pihole/gravity.db" + macvendor: "/etc/pihole/macvendor.db" + setupVars: "/etc/pihole/setupVars.conf" + http_info: "/var/log/pihole/HTTP_info.log" + ph7_error: "/var/log/pihole/PH7.log" + misc: + nice: -10 + delay_startup: 10 + addr2line: true + privacylevel: 0 + check: + load: true + shmem: 90 + disk: 90 + debug: + database: false + networking: false + locks: false + queries: false + flags: false + shmem: false + gc: false + arp: false + regex: false + api: false + overtime: false + status: false + caps: false + dnssec: false + vectors: false + resolver: false + edns0: false + clients: false + aliasclients: false + events: false + helper: false + config: false + extra: false + reserved: false + parameters: + detailed: + name: detailed + in: query + description: Return detailed information about the configuration + required: false + schema: + type: boolean + default: false + example: false diff --git a/src/api/docs/docs.h b/src/api/docs/docs.h index e450cdc0..52844e44 100644 --- a/src/api/docs/docs.h +++ b/src/api/docs/docs.h @@ -103,6 +103,14 @@ static const char specs_stats_yaml[] = { static const char specs_version_yaml[] = { #include "hex/specs/version.yaml" }; + +static const char specs_config_yaml[] = { +#include "hex/specs/config.yaml" +}; + +static const char specs_network_yaml[] = { +#include "hex/specs/network.yaml" +}; struct { const char *path; const char *mime_type; @@ -132,6 +140,8 @@ struct { {"specs/queries.yaml", "text/plain", specs_queries_yaml, sizeof(specs_queries_yaml)}, {"specs/stats.yaml", "text/plain", specs_stats_yaml, sizeof(specs_stats_yaml)}, {"specs/version.yaml", "text/plain", specs_version_yaml, sizeof(specs_version_yaml)}, + {"specs/config.yaml", "text/plain", specs_config_yaml, sizeof(specs_config_yaml)}, + {"specs/network.yaml", "text/plain", specs_network_yaml, sizeof(specs_network_yaml)}, }; #endif // API_DOCS_H \ No newline at end of file diff --git a/src/config/config.c b/src/config/config.c index 5e28e7a6..bd6f1424 100644 --- a/src/config/config.c +++ b/src/config/config.c @@ -43,51 +43,51 @@ void set_all_debug(const bool status) // Extract and store key from full path static char **gen_config_path(const char *pathin) { - char *path = (char*)pathin; - char *saveptr = path; + char *path = (char*)pathin; + char *saveptr = path; - // Sanity check - if(!pathin) - { - log_err("Config path is empty"); - return NULL; - } + // Sanity check + if(!pathin) + { + log_err("Config path is empty"); + return NULL; + } - // Allocate memory for the path elements - char **paths = calloc(MAX_CONFIG_PATH_DEPTH, sizeof(char*)); - //char *token; + // Allocate memory for the path elements + char **paths = calloc(MAX_CONFIG_PATH_DEPTH, sizeof(char*)); + //char *token; - size_t pathlen = 0; - // Extract all path elements - while(*path != '\0') - { - // Advance to either the next delimiter - // But only until the end of the string - while(*path != '.' && *path != '\0') - path++; + size_t pathlen = 0; + // Extract all path elements + while(*path != '\0') + { + // Advance to either the next delimiter + // But only until the end of the string + while(*path != '.' && *path != '\0') + path++; - // Get length of the extracted string - size_t len = path - saveptr; - // Create a private copy of this element in the chain of elements - paths[pathlen] = calloc(len + 1, sizeof(char)); - // No need to NULL-terminate, strncpy does this for us - strncpy(paths[pathlen], saveptr, len); + // Get length of the extracted string + size_t len = path - saveptr; + // Create a private copy of this element in the chain of elements + paths[pathlen] = calloc(len + 1, sizeof(char)); + // No need to NULL-terminate, strncpy does this for us + strncpy(paths[pathlen], saveptr, len); - // Did we reach the end of the string? - if(*path == '\0') - break; + // Did we reach the end of the string? + if(*path == '\0') + break; - // Advance to next character - saveptr = ++path; - // Advance to next path element - pathlen++; + // Advance to next character + saveptr = ++path; + // Advance to next path element + pathlen++; - // Safetly measure: Exit if this path is too deep - if(pathlen > MAX_CONFIG_PATH_DEPTH-1) - break; - } + // Safetly measure: Exit if this path is too deep + if(pathlen > MAX_CONFIG_PATH_DEPTH-1) + break; + } - return paths; + return paths; } struct conf_item *get_conf_item(const unsigned int n) @@ -95,7 +95,7 @@ struct conf_item *get_conf_item(const unsigned int n) // Sanity check if(n > CONFIG_ELEMENTS-1) { - log_err("Config item with index %u requested but we have only %lu elements", n, CONFIG_ELEMENTS-1); + log_err("Config item with index %u requested but we have only %u elements", n, (unsigned int)CONFIG_ELEMENTS-1); return NULL; } @@ -143,7 +143,7 @@ void initConfig(void) config.dns.blockESNI.d.b = true; config.dns.EDNS0ECS.k = "dns.EDNS0ECS"; - config.dns.EDNS0ECS.h = "Should _esni. subdomains be blocked by default?"; + config.dns.EDNS0ECS.h = "Should FTL analyze possible ECS information to obtain client IPs hidden behind NATs?"; config.dns.EDNS0ECS.t = CONF_BOOL; config.dns.EDNS0ECS.d.b = true; @@ -293,12 +293,12 @@ void initConfig(void) config.database.DBexport.d.b = true; config.database.maxDBdays.k = "database.maxDBdays"; - config.database.maxDBdays.h = "How much history should be imported from the database [seconds]? (max 24*60*60 = 86400)"; + config.database.maxDBdays.h = "How long should queries be stored in the database [days]?"; config.database.maxDBdays.t = CONF_INT; config.database.maxDBdays.d.i = 365; config.database.maxHistory.k = "database.maxHistory"; - config.database.maxHistory.h = "How long should queries be stored in the database [days]?"; + config.database.maxHistory.h = "How much history should be imported from the database [seconds]? (max 24*60*60 = 86400)"; config.database.maxHistory.t = CONF_UINT; config.database.maxHistory.d.ui = MAXLOGAGE*3600; @@ -605,7 +605,7 @@ void initConfig(void) // Verify all config options are defined above if(!conf_item->p) - log_err("Config option %u/%lu is not set!", i, CONFIG_ELEMENTS); + log_err("Config option %u/%u is not set!", i, (unsigned int)CONFIG_ELEMENTS); else if(conf_item->p[3]) log_debug(DEBUG_CONFIG, "Config option %u is %s.%s.%s.%s", i, conf_item->p[0], conf_item->p[1], conf_item->p[2], conf_item->p[3]); diff --git a/src/config/toml_writer.c b/src/config/toml_writer.c index f94b19b2..af596439 100644 --- a/src/config/toml_writer.c +++ b/src/config/toml_writer.c @@ -79,7 +79,8 @@ bool writeFTLtoml(void) writeTOMLvalue(fp, conf_item->t, &conf_item->v); // Compare with default value and add a comment on difference - if(memcmp(&conf_item->v, &conf_item->d, sizeof(conf_item->v)) != 0) + if((conf_item->t == CONF_STRING && strcmp(conf_item->v.s, conf_item->d.s) != 0) || + (conf_item->t != CONF_STRING && memcmp(&conf_item->v, &conf_item->d, sizeof(conf_item->v)) != 0)) { fprintf(fp, " ### CHANGED, default = "); writeTOMLvalue(fp, conf_item->t, &conf_item->d); diff --git a/test/api/libs/FTLAPI.py b/test/api/libs/FTLAPI.py index e576f20f..59b68465 100644 --- a/test/api/libs/FTLAPI.py +++ b/test/api/libs/FTLAPI.py @@ -10,6 +10,7 @@ # Please see LICENSE file for your rights under this license. import urllib.request +from typing import List import json # Class to query the FTL API @@ -20,7 +21,7 @@ class FTLAPI(): self.errors = [] # Query the FTL API and return the response - def getFTLresponse(self, uri: str, params: list[str] = []): + def getFTLresponse(self, uri: str, params: List[str] = []): self.errors = [] try: if len(params) > 0: diff --git a/test/pihole-FTL.toml b/test/pihole-FTL.toml index b00da123..99f8da8e 100644 --- a/test/pihole-FTL.toml +++ b/test/pihole-FTL.toml @@ -3,13 +3,9 @@ # Do not edit the file while FTL is # running or your changes may be overwritten # -# Last update: 2021-06-10 11:36:29 +# Last update: 2023-01-07 18:28:45 [dns] - # How should FTL reply to blocked queries? - # Possible values are: [ "NULL", "IP-NODATA-AAAA", "IP", "NXDOMAIN" ] - blockingmode = "NULL" - # Should FTL walk CNAME paths? CNAMEdeepInspect = true @@ -25,6 +21,12 @@ # Should FTL should internally generated DNSSEC queries? showDNSSEC = true + # Should FTL analyze AAAA queries? + analyzeAAAA = true + + # Should FTL analyze *only* A and AAAA queries? + analyzeOnlyAandAAAA = false + # Should FTL return "pi.hole" as name for PTR requests to local IP addresses? # Possible values are: [ "NONE", "HOSTNAME", "HOSTNAMEFQDN", "PI.HOLE" ] piholePTR = "PI.HOLE" @@ -36,11 +38,9 @@ # TTL for blocked queries [seconds] blockTTL = 2 - # Should FTL analyze AAAA queries? - analyzeAAAA = true - - # Should FTL analyze only A and AAAA queries? - analyzeOnlyAandAAAA = false + # How should FTL reply to blocked queries? + # Possible values are: [ "NULL", "IP-NODATA-AAAA", "IP", "NXDOMAIN" ] + blockingmode = "NULL" [dns.specialDomains] # Should FTL handle use-application-dns.net specifically and always return NXDOMAIN? @@ -49,22 +49,33 @@ # Should FTL handle the iCloud privacy relay domains specifically and always return NXDOMAIN? iCloudPrivateRelay = true - [dns.reply] [dns.reply.host] - # Use a specific IPv4 address for the Pi-hole host - # Possible values are: or empty string ("") - IPv4 = "10.100.0.10" ### CHANGED, default = "" + # Use a specific IPv4 address for the Pi-hole host? + overwrite_v4 = true ### CHANGED, default = false - # Use a specific IPv6 address for the Pi-hole host + # Use a specific IPv6 address for the Pi-hole host? + overwrite_v6 = true ### CHANGED, default = false + + # Custom IPv4 address for the Pi-hole host + # Possible values are: or empty string ("") + IPv4 = "10.100.0.10" ### CHANGED, default = " + + # Custom IPv6 address for the Pi-hole host # Possible values are: or empty string ("") IPv6 = "fe80::10" ### CHANGED, default = "" [dns.reply.blocking] - # Use a specific IPv4 address in IP blocking mode + # Use a specific IPv4 address in IP blocking mode? + overwrite_v4 = true ### CHANGED, default = false + + # Use a specific IPv6 address in IP blocking mode? + overwrite_v6 = true ### CHANGED, default = false + + # Custom IPv4 address for IP blocking mode # Possible values are: or empty string ("") IPv4 = "10.100.0.11" ### CHANGED, default = "" - # Use a specific IPv6 address in IP blocking mode + # Custom IPv6 address for IP blocking mode # Possible values are: or empty string ("") IPv6 = "fe80::11" ### CHANGED, default = "" @@ -72,7 +83,7 @@ # How many queries are permitted... count = 0 ### CHANGED, default = 1000 - # ..in the set interval before rate-limiting? + # ... in the set interval before rate-limiting? interval = 0 ### CHANGED, default = 60 [resolver] @@ -82,7 +93,7 @@ # Should FTL try to resolve IPv6 addresses to hostnames? resolveIPv6 = false ### CHANGED, default = true - # Try to obtain client names from the network table + # Try to obtain client names from the network table? networkNames = false ### CHANGED, default = true # How (and if) hourly PTR lookups should be made @@ -114,9 +125,9 @@ [http] # Does local clients need to authenticate to access the API? - localAPIauth = true + localAPIauth = false ### CHANGED, default = true - # Should FTL insert extra spaces to prettify the API output? + # Should FTL prettify the API output? prettyJSON = false # How long should a session be considered valid after login [seconds]? @@ -126,12 +137,12 @@ # Possible values are: domain = "pi.hole" - # Webserver access control list. + # Webserver access control list # Possible values are: acl = "+0.0.0.0/0" # Ports to be used by the webserver - # Possible values are: list of <[ip_address:]port> + # Possible values are: comma-separated list of <[ip_address:]port> port = "8080,[::]:8080" [http.paths] @@ -139,7 +150,7 @@ # Possible values are: webroot = "/var/www/html" - # From which sub-directory is the web interface served from? + # Sub-directory of the root containing the web interface # Possible values are: , both slashes are needed! webhome = "/admin/" @@ -157,115 +168,118 @@ database = "/etc/pihole/pihole-FTL.db" # The location of Pi-hole's gravity database - # Possible values are: + # Possible values are: gravity = "/etc/pihole/gravity.db" # The database containing MAC -> Vendor information for the network table - # Possible values are: + # Possible values are: macvendor = "/etc/pihole/macvendor.db" # The config file of Pi-hole - # Possible values are: + # Possible values are: setupVars = "/etc/pihole/setupVars.conf" # The log file used by the webserver - # Possible values are: - HTTPinfo = "/var/log/pihole/HTTP_info.log" + # Possible values are: + http_info = "/var/log/pihole/HTTP_info.log" # The log file used by the dynamic interpreter PH7 # Possible values are: - PH7error = "/var/log/pihole/PH7.log" + ph7_error = "/var/log/pihole/PH7.log" [misc] - # Privacy level - privacyLevel = 0 - # Set niceness of pihole-FTL (can be disabled by setting to -999) nice = -999 ### CHANGED, default = -10 - # Artificially delay FTL's startup (0 to 300 seconds) - delayStartup = 0 - # Should FTL try to call addr2line when generating backtraces? + delay_startup = 0 + + # The log file used by the dynamic interpreter PH7 addr2line = true + # Privacy level + privacylevel = 0 + [misc.check] # Should FTL check the 15 min average of CPU load and complain if the load is larger than the number of available CPU cores? - load = false + load = false ### CHANGED, default = true - # Limit above which FTL should complain about a shared-memory shortage - disk = 0 + # Limit above which FTL should complain about disk shortage for checked files [percent] + shmem = 0 ### CHANGED, default = 90 - # Limit above which FTL should complain about disk shortage for checked files - shmem = 0 + # Limit above which FTL should complain about a shared-memory shortage [percent] + disk = 0 ### CHANGED, default = 90 [debug] - # Temporarily enable all debug flags - all = true ### CHANGED, default = false - # Enable extra logging of database actions - database = false + database = true ### CHANGED, default = false # Enable extra logging of detected interfaces - networking = false + networking = true ### CHANGED, default = false # Enable extra logging of shared memory lock actions - locks = false + locks = true ### CHANGED, default = false # Print extensive query information - queries = false + queries = true ### CHANGED, default = false # Print flags of queries received by the DNS hooks - flags = false + flags = true ### CHANGED, default = false # Print information about shared memory buffers - shmem = false + shmem = true ### CHANGED, default = false # Print information about garbage collection - gc = false + gc = true ### CHANGED, default = false # Print information about ARP table processing - arp = false + arp = true ### CHANGED, default = false # Enable extra logging of regex matching details - regex = false + regex = true ### CHANGED, default = false # Enable extra logging of API activities - api = false + api = true ### CHANGED, default = false # Print information about overTime memory operations - overtime = false + overtime = true ### CHANGED, default = false # Enable extra logging of query status changes - status = false + status = true ### CHANGED, default = false # Print information about capabilities granted to the pihole-FTL process - caps = false + caps = true ### CHANGED, default = false - # Enable extra logging in dnsmasq's log routine - dnsmasq_lines = false + # Print information about DNSSEC activity + dnssec = true ### CHANGED, default = false # Print vector operation details - vectors = false + vectors = true ### CHANGED, default = false # Extensive information about hostname resolution like which DNS servers are used - resolver = false + resolver = true ### CHANGED, default = false # Print EDNS(0) debugging information - edns0 = false + edns0 = true ### CHANGED, default = false # Enable extra client detail logging - clients = false + clients = true ### CHANGED, default = false # Print aliasclient details - aliasclients = false + aliasclients = true ### CHANGED, default = false # Log information about processed internal events - events = false + events = true ### CHANGED, default = false # Enable logging of script helper activity - helper = false + helper = true ### CHANGED, default = false # Print config parsing details - config = false + config = true ### CHANGED, default = false + + # Special debug flag that may be used for debugging specific issues + extra = true ### CHANGED, default = false + + # Reserved debug flag + reserved = true ### CHANGED, default = false