├── .github └── FUNDING.yml ├── .gitignore ├── .travis.yml ├── 01-dnssec-trigger.in ├── Changelog ├── INSTALL ├── LICENSE ├── Makefile.in ├── README ├── README.md ├── acx_nlnetlabs.m4 ├── compat ├── inet_ntop.c ├── inet_pton.c ├── malloc.c ├── memmove.c ├── snprintf.c └── strlcpy.c ├── config.h.in ├── configure ├── configure.ac ├── contrib └── README ├── dnssec-trigger-control-setup.sh.in ├── dnssec-trigger-control.c ├── dnssec-trigger-netconfig-hook.sh.in ├── dnssec-trigger-script.in ├── dnssec-trigger.8.in ├── dnssec-triggerd-keygen.service ├── dnssec-triggerd.service.in ├── dnssec.conf ├── example.conf.in ├── fedora ├── tmpfiles-unbound.conf ├── unbound-keygen.service ├── unbound.service └── unbound.spec ├── install-sh ├── makedist.sh ├── osx ├── RiggerStatusItem │ ├── English.lproj │ │ ├── InfoPlist.strings │ │ └── MainMenu.xib │ ├── RiggerApp.h │ ├── RiggerApp.m │ ├── RiggerStatusItem-Info.plist │ ├── RiggerStatusItem.xcodeproj │ │ └── project.pbxproj.in │ ├── RiggerStatusItemAppDelegate.h │ ├── RiggerStatusItemAppDelegate.m │ ├── RiggerStatusItem_Prefix.pch │ ├── main.m │ ├── status-icon-alert.png │ └── status-icon.png ├── dnssec-trigger-osx.sh.in ├── dnssec-trigger-setdns.sh.in ├── nl.nlnetlabs.dnssec-trigger-hook.plist.in ├── nl.nlnetlabs.dnssec-trigger-panel.plist.in ├── nl.nlnetlabs.dnssec-triggerd.plist.in ├── pkg │ ├── dmg-template.dmg.gz │ ├── makepackage │ └── package-bg.png ├── wakelist.c └── wakelist.h ├── panel ├── attach.c ├── attach.h ├── dmg-icon.png ├── dmg-icon.svg ├── dnssec-trigger-panel.desktop.in ├── install-icon.png ├── install-icon.svg ├── panel.c ├── pui.xml ├── status-icon-alert.png ├── status-icon-alert.svg ├── status-icon.png ├── status-icon.svg ├── uninstall-icon.png └── uninstall-icon.svg ├── riggerd ├── cfg.c ├── cfg.h ├── connection_list.c ├── connection_list.h ├── fptr_wlist.c ├── fptr_wlist.h ├── fwd_zones.c ├── fwd_zones.h ├── http.c ├── http.h ├── lock.c ├── lock.h ├── log.c ├── log.h ├── mini_event.c ├── mini_event.h ├── net_help.c ├── net_help.h ├── netevent.c ├── netevent.h ├── probe.c ├── probe.h ├── rbtree.c ├── rbtree.h ├── reshook.c ├── reshook.h ├── riggerd.c ├── store.c ├── store.h ├── string_buffer.h ├── string_list.c ├── string_list.h ├── svr.c ├── svr.h ├── ubhook.c ├── ubhook.h ├── update.c ├── update.h ├── winsock_event.c └── winsock_event.h ├── test ├── clang-analysis.sh ├── json.c ├── list_forwards_example ├── list_local_zones_example ├── other.c ├── servers-list-ipv4 ├── tmp │ └── commit-cache └── unbound-control-fake.sh ├── vendor └── ccan │ └── json │ ├── BSD-MIT │ ├── _info │ ├── json.c │ ├── json.h │ └── test │ ├── common.h │ ├── run-construction.c │ ├── run-decode-encode.c │ ├── run-stringify.c │ ├── run-validate.c │ ├── test-strings │ └── test-strings-reencoded └── winrc ├── alert.ico ├── combined.ico ├── dnssec-trigger-keygen.c ├── dnssec-trigger64.png ├── gen_msg.bin ├── gen_msg.mc ├── gtkrc ├── install.ico ├── netlist.c ├── netlist.h ├── panel.manifest ├── proc.dll ├── proc_dll_src ├── Processes.dll ├── exdll.c ├── exdll.h ├── license.rtf ├── make.sh ├── proc.dll ├── processes.c ├── processes.h ├── processes.rc ├── processes.sln ├── processes.suo ├── processes.txt ├── processes.vcproj ├── readme.txt ├── resource.h ├── stdafx.cpp ├── stdafx.h └── stdafx_orig.h ├── rsrc_control.rc ├── rsrc_keygen.rc ├── rsrc_panel.rc ├── rsrc_triggerd.rc ├── setup.nsi ├── setup_left.bmp ├── setup_left_un.bmp ├── setup_top.bmp ├── status.ico ├── trayicon.c ├── uninstall.ico ├── vista_admin.manifest ├── vista_user.manifest ├── w_inst.c ├── w_inst.h ├── win_svc.c └── win_svc.h /.github/FUNDING.yml: -------------------------------------------------------------------------------- 1 | github: [NLnetLabs] 2 | custom: ['https://nlnetlabs.nl/funding/'] 3 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | /Makefile 2 | /config.h 3 | /config.h.in~ 4 | /config.log 5 | /config.status 6 | /autom4te.cache 7 | /01-dnssec-trigger 8 | /build 9 | /dnssec-trigger-control 10 | /dnssec-trigger-control-setup 11 | /dnssec-trigger-panel 12 | /dnssec-trigger-panel.desktop 13 | /dnssec-trigger-script 14 | /dnssec-trigger.8 15 | /dnssec-triggerd 16 | /dnssec-triggerd.service 17 | /example.conf 18 | /test/json-test 19 | /test/other-test 20 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | sudo: false 2 | language: c 3 | compiler: 4 | - gcc 5 | addons: 6 | apt: 7 | packages: 8 | - libssl-dev 9 | - libgtk2.0-dev 10 | - libglib2.0-dev 11 | - libldns-dev 12 | - clang 13 | script: 14 | - ./configure --enable-debug --with-forward-zones-support 15 | - make 16 | - make test 17 | -------------------------------------------------------------------------------- /01-dnssec-trigger.in: -------------------------------------------------------------------------------- 1 | #!@SHELL@ 2 | # 3 | # Script to notify dnssec-trigger that the DNS configuration in NetworkManager 4 | # may have changed. 5 | 6 | # Future versions of NetworkManager will have an active unbound/dnssec-trigger 7 | # plugin. Don't intervene when the new plugin is being used. 8 | if [ -e /etc/NetworkManager/NetworkManager.conf ]; then 9 | grep -q '^dns=unbound\>' /etc/NetworkManager/NetworkManager.conf && exit 0 10 | fi 11 | 12 | # Exec the dnssec-trigger update script that uses NetworkManager API to gather 13 | # all the necessary information. 14 | if [ -x @libexecdir@/dnssec-trigger-script ]; then 15 | exec @libexecdir@/dnssec-trigger-script --@NMDISPATCHERCOMMAND@ 16 | fi 17 | 18 | # When dnssec-trigger-script is absent or not executable, the original 19 | # shell-based dnssec trigger hook code below is run instead. 20 | # 21 | # NetworkManager trigger for in dispatcher.d 22 | # config items 23 | # set PATH correctly instead of absolute paths to binaries 24 | PATH="@sbindir@:@bindir@:/sbin:/usr/sbin:/bin:/usr/bin" 25 | 26 | state_dir="/var/run/dnssec-trigger" 27 | validate_forward_zones="no" 28 | 29 | # implementation 30 | ifname="$1" 31 | action="$2" 32 | domains="" 33 | nameservers="" 34 | global_nameservers="" 35 | conn_zones_file="$state_dir/$CONNECTION_UUID" 36 | 37 | ################################################################ 38 | # get domains and nameservers if provided by connection going up 39 | case "$action" in 40 | "vpn-up" ) 41 | domains="`echo $VPN_IP4_DOMAINS $VPN_IP6_DOMAINS | tr " " "\n" | sort -u | tr "\n" " " | sed '$s/.$//'`" 42 | nameservers="`echo $VPN_IP4_NAMESERVERS $VPN_IP6_NAMESERVERS`" 43 | ;; 44 | "up" ) 45 | domains="`echo $IP4_DOMAINS $IP6_DOMAINS | tr " " "\n" | sort -u | tr "\n" " " | sed '$s/.$//'`" 46 | nameservers="`echo $IP4_NAMESERVERS $IP6_NAMESERVERS`" 47 | ;; 48 | esac 49 | 50 | ######################### 51 | # get global nameservers 52 | # try to get nmcli version 53 | NMCLI_VER=$(printf '%03d%03d%03d%03d\n' $(nmcli -v 2>/dev/null | sed 's/.*version \([0-9]\+\)\.\([0-9]\+\)\.\([0-9]\+\)\.\([0-9]\+\).*/\1 \2 \3 \4/')) 54 | # if nmcli exists 55 | if [ -n "$NMCLI_VER" ]; then 56 | # if the version is greater or equal 0.9.9.0 57 | if [ $NMCLI_VER -ge 000009009000 ]; then 58 | global_nameservers="`nmcli -f IP4,IP6 dev show | fgrep 'DNS' | awk '{print $2;}'`" 59 | else 60 | global_nameservers="`nmcli -f IP4,IP6 dev list | fgrep 'DNS' | awk '{print $2;}'`" 61 | fi 62 | # nmcli does not exist 63 | else 64 | global_nameservers="`nm-tool | grep 'DNS:' | awk '{print $2;}'`" 65 | fi 66 | # fix whitespaces 67 | global_nameservers="`echo $global_nameservers`" 68 | 69 | 70 | ############################################################ 71 | # configure global nameservers using dnssec-trigger-control 72 | if [ -n "`pidof dnssec-triggerd`" ] ; then 73 | dnssec-trigger-control submit "$global_nameservers" &> /dev/null 74 | logger "dnssec-trigger-hook(networkmanager) $ifname $action added global DNS $global_nameservers" 75 | else 76 | logger "dnssec-trigger-hook(networkmanager) $ifname $action NOT added global DNS - dnssec-triggerd is not running" 77 | fi 78 | 79 | ###################################################### 80 | # add forward zones into unbound using unbound-control 81 | if [ -n "`pidof unbound`" ]; then 82 | if [ -r "$conn_zones_file" ]; then 83 | for domain in `cat $conn_zones_file`; do 84 | # Remove forward zone from unbound 85 | if [ "$validate_forward_zones" = "no" ]; then 86 | unbound-control forward_remove +i $domain &> /dev/null 87 | else 88 | unbound-control forward_remove $domain &> /dev/null 89 | fi 90 | unbound-control flush_zone $domain &> /dev/null 91 | unbound-control flush_requestlist &> /dev/null 92 | 93 | logger "dnssec-trigger-hook(networkmanager) $ifname $action removed forward DNS zone $domain" 94 | done 95 | 96 | # Remove file with zones for this connection 97 | rm -f $conn_zones_file &> /dev/null 98 | fi 99 | 100 | if [ "$action" = "vpn-up" -o "$action" = "up" ]; then 101 | if [ -n "$domains" ]; then 102 | for domain in $domains; do 103 | # Add forward zone into unbound 104 | if [ "$validate_forward_zones" = "no" ]; then 105 | unbound-control forward_add +i $domain $nameservers &> /dev/null 106 | else 107 | unbound-control forward_add $domain $nameservers &> /dev/null 108 | fi 109 | unbound-control flush_zone $domain &> /dev/null 110 | unbound-control flush_requestlist &> /dev/null 111 | 112 | # Create zone info file 113 | mkdir -p $(dirname $conn_zones_file) 114 | echo $domain >> $conn_zones_file 115 | 116 | logger "dnssec-trigger-hook(networkmanager) $ifname $action added forward DNS zone $domain $nameservers" 117 | done 118 | fi 119 | fi 120 | else 121 | logger "dnssec-trigger-hook(networkmanager) $ifname $action NOT added forward DNS zone(s) - unbound is not running" 122 | fi 123 | 124 | exit 0 125 | -------------------------------------------------------------------------------- /INSTALL: -------------------------------------------------------------------------------- 1 | Helpful install instructions for dnssec-trigger. 2 | 3 | Quick overview 4 | -------------- 5 | The software installs several components 6 | * the dnssec-triggerd daemon that does probes, it needs to be started on boot. 7 | * the dnssec-trigger-panel that shows a status icon in the tray. it needs 8 | to be in the user startup items. It can be gtk or cocoa. 9 | * some sort of hook script that catches DHCP updates, system specific. 10 | it can be networkmanager, netconfig, osx or windows. 11 | 12 | Before you install you need: gcc, openssl-dev, gtk2-dev, glib-dev and install 13 | unbound (as a server on 127.0.0.1 that starts on boot), and libldns-dev. 14 | On OSX, gtk2 and glib are not needed, but XCode is used for cocoa. 15 | 16 | The compile process is ./configure && make, as usual. 17 | 18 | There are a bunch of configure options to put files in different locations, 19 | and to change defaults. 20 | 21 | If you do not want to install libldns (for some reason) or libcrypto, 22 | you can use --enable-static-exe, and provide --with-ldns= and --with-ssl= options. It will 24 | statically link with openssl and ldns. 25 | 26 | Install (Linux) 27 | --------------- 28 | 1. Install required libraries and get the dnssec-trigger package. 29 | On Ubuntu you must install libappindicator-dev, so it builds for Unity GUI. 30 | 2. ./configure 31 | It needs to detect what sort of system you use - to hook into the DHCP 32 | network updates. For many linux systems, networkmanager or netconfig. 33 | Default puts files in /usr/local 34 | 3. make 35 | It could complain about missing libraries here. Install them, back to 2. 36 | 4. sudo make install 37 | Install as root. Note you can uninstall with make uninstall. 38 | 5. sudo dnssec-trigger-control-setup 39 | This should create the key files that dnssec-trigger uses to communicate 40 | securely between its components. 41 | 6. edit unbound.conf to allow remote-control: 42 | sudo dnssec-trigger-control-setup -i 43 | if you want you can edit by hand, we need root anchor and remote-control 44 | 7. setup dnssec-triggerd to start on boot. 45 | some script in /etc/rc.d or so. 46 | Or you can start it with sudo dnssec-triggerd (just this once). 47 | The startup script needs to call dnssec-trigger-control submit 48 | with a list of nameserver IPs (it may be the empty list), this will 49 | cause the server to initialise. It may be possible to call the 50 | DHCP change hook for this from the startup script. 51 | 8. the dnssec-trigger-panel needs to start for users on login. 52 | to this end a .desktop file is installed in /etc/xdg/autostart for GNOME. 53 | Or you can start it from the commandline (just this once). 54 | 55 | On uninstall you may need to chmod 644 /etc/resolv.conf 56 | so that it becomes writable again. To remove the system specific DNS 57 | override, dnssec-triggerd -u can be used. 58 | 59 | Install (OSX) 60 | ------------- 61 | Same as on Linux, but step 7 and 8 are taken care of by putting plist files 62 | in the LaunchAgents folder. On OSX prior to 10.5 it puts the user login 63 | start item enabled for you, but make uninstall cannot disable it, you have 64 | to manually perform this from the user-account control panel. On OSX 10.5 65 | and later, a launchAgent plist item does the job and is installed and 66 | uninstalled for you. 67 | 68 | On OSX a cocoa user interface is built instead of GTK, to display the status 69 | icon on the top right of the menu bar. 70 | 71 | Test (Demonstration) 72 | -------------------- 73 | Since all the DHCP hook does is call dnssec-trigger-control submit 74 | and then those caches are probed and configuration is changed, you can use 75 | that to test. Simply sudo dnssec-trigger-control submit 127.0.0.3. 76 | Assuming there is nothing on that address (usually true), it times out and 77 | you see that the authority servers on the internet are used instead. 78 | If you want to test a failure of the network to allow DNSSEC traffic, you 79 | can use the command sudo dnssec-trigger-control unsafe. It causes the 80 | daemon to use another couple 127.0.0.x addresses (that should not answer) 81 | and a second later think that DNSSEC does not work at all. The popup window 82 | should show, if you select insecure, it then uses those 127.0.0.x addresses 83 | which will of course not really answer at all. It demonstrates the GUI. 84 | 85 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Copyright (c) 2011, NLnet Labs. All rights reserved. 2 | 3 | This software is open source. 4 | 5 | Redistribution and use in source and binary forms, with or without 6 | modification, are permitted provided that the following conditions 7 | are met: 8 | 9 | Redistributions of source code must retain the above copyright notice, 10 | this list of conditions and the following disclaimer. 11 | 12 | Redistributions in binary form must reproduce the above copyright notice, 13 | this list of conditions and the following disclaimer in the documentation 14 | and/or other materials provided with the distribution. 15 | 16 | Neither the name of the NLNET LABS nor the names of its contributors may 17 | be used to endorse or promote products derived from this software without 18 | specific prior written permission. 19 | 20 | THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 21 | "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 22 | LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 23 | A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 24 | HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 25 | SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 26 | TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 27 | PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 28 | LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 29 | NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 30 | SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 31 | -------------------------------------------------------------------------------- /README: -------------------------------------------------------------------------------- 1 | Dnssec Trigger Readme 2 | 3 | By Wouter Wijngaards, NLnet Labs, 2011 4 | BSD license is in the LICENSE file. 5 | Bugs or comments: labs@nlnetlabs.nl 6 | 7 | To install see the INSTALL instructions file. 8 | 9 | Intro 10 | ----- 11 | 12 | This package contains the dnssec-trigger tools. It works together with 13 | a local validating resolver (unbound) and keeps DNSSEC enabled. It does 14 | so by selecting DNSSEC enabled upstream caches or servers for unbound 15 | to talk to and by modifying the DNS path on the system to 127.0.0.1. 16 | If DNSSEC does not work because of middleboxes, the insecure option 17 | (after a dialog window for the user) causes the DNS path to be set to 18 | the insecure servers. 19 | 20 | The main components are the daemon, DHCP-hooks, and a GUI-panel. 21 | The daemon starts at bootup and runs in the background. The DHCP hooks 22 | tell the daemon, these are sometimes scripts depending on the system. 23 | The GUI-panel shows a tray icon notification applet. The GUI panel shows 24 | the dialog to the user if insecure is the only option. The GUI panel 25 | has a Reprobe button, so after sigon for the hotspot the user can retry 26 | (it makes the red ! disappear if it works). 27 | 28 | Applications can then trust responses with the AD flag from 127.0.0.1. 29 | But they should know that sometimes the resolv.conf contains 'bad' 30 | insecure servers (not 127.0.0.1) and then they must not trust the AD 31 | flag from them (and may need to send the query without the DO flag 32 | to fallback). Responses asked with DO flag to 127.0.0.1 and with the 33 | returned AD flag can then be trusted. Trusted DNS responses may help 34 | with DANE. 35 | 36 | The dnssec-trigger package thus runs alongside the unbound daemon. It 37 | provides the user with the option to go to Insecure. It selects DNSSEC 38 | service where possible. This helps people run DNSSEC. 39 | 40 | 41 | Normal usage 42 | ------------ 43 | 44 | The user logs in and sees a status icon in the tray. Most of the time 45 | it displays no ! (exclamation) but is quiet. The icon can be ignored. 46 | 47 | When the user connects to a new network, the DHCP hooks notify the 48 | dnssec-trigger daemon. This probes the network, and notifies unbound. 49 | The user sees no change and continues to ignore the icon, unless there 50 | is no DNSSEC. 51 | 52 | If the daemon probe fails to find DNSSEC capability, it tells unbound 53 | to stop talking to the network, and tells the statusicon to ask the user. 54 | A dialog pops up out of the tray icon. If insecure, then the resolv.conf 55 | is changed to the insecure servers, unbound is inactive (loops to 56 | 127.0.0.127). The user can work normally on this network connection. 57 | 58 | For a hotspot, the probe would fail (after a second or two), then with 59 | insecure mode the user can login to the hotspot. With Reprobe menu 60 | item the user can reprobe dnssec and if it works then (many hotspots 61 | provide good access once logged in) the icon is restored to safe. The 62 | scripts would also reprobe on a DHCP change. 63 | 64 | 65 | Operations on Platforms 66 | ----------------------- 67 | 68 | How the different platforms operate is described here. 69 | 70 | * Security 71 | 72 | There used to be a race condition where DHCP info briefly overriddes 73 | the secure version, but this was fixed in 0.6. 74 | 75 | * unix - NetworkManager 76 | 77 | In /etc/NetworkManager/dispatcher.d a script sends DHCP changes to 78 | the daemon. The script is a networkmanager dhcp hook script and uses 79 | dnssec-trigger-control to talk to the daemon. The script uses nmcli 80 | to find the DNS info. 81 | 82 | GTK user interface. In /etc/xdg/autostart/ a .desktop entry starts 83 | the user-side tray icon (dnssec-trigger-panel). The daemon is started 84 | from /etc/rc.d like regular daemons. The tray icon communicates with 85 | the daemon over a persistent SSL connection over loopback (127.0.0.1). 86 | It is possible to have multiple tray icons connected over SSL. 87 | 88 | * unix - Netconfig 89 | 90 | In /etc/netconfig.d a script sends DHCP changes to the daemon. It greps 91 | the info out of /var/run/netconfig/* files. It sends with 92 | dnssec-trigger-control to the daemon. 93 | 94 | GTK like networkmanager. 95 | 96 | * OSX 97 | 98 | In /Library/LaunchDaemons two plist files exist. One starts the daemon. 99 | The other watches the /Library/Preferences/SystemConfiguration for changes 100 | and launches a script. This script uses ifconfig and parses plist files 101 | and then sends the results with dnssec-trigger-control to the daemon. 102 | 103 | The daemon changes resolv.conf but does not need to as on OSX it also 104 | sets the network preferences for the network interfaces to the values. 105 | These preferences survive a reboot, so the reboot is safe. There then 106 | is no connection until unbound is started during reboot. 107 | 108 | In /Library/LaunchAgents a plist file starts the tray icon (Cocoa app). 109 | It uses an SSL connection to the daemon over loopback (127.0.0.1). 110 | 111 | * Windows 112 | 113 | The daemon is a service. It has a thread that listens to network changes 114 | and blocks on that, it notifies the main daemon when there is a change. 115 | The DHCP DNS servers are picked from the registry and the override DNS 116 | options are put in the registry as the network preferences. These survive 117 | a reboot, so that the system is safe during a reboot. There then is no 118 | DNS connection until unbound is started during reboot. 119 | 120 | The tray icon is a native application. It uses SSL to talk to the daemon. 121 | 122 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Dnssec-Trigger 2 | 3 | [![Travis Build Status](https://travis-ci.com/NLnetLabs/dnssec-trigger.svg?branch=master)](https://travis-ci.com/NLnetLabs/dnssec-trigger) 4 | [![Packaging status](https://repology.org/badge/tiny-repos/dnssec-trigger.svg)](https://repology.org/project/dnssec-trigger/versions) 5 | 6 | By Wouter Wijngaards, NLnet Labs, 2011 \ 7 | BSD license is in the LICENSE file. \ 8 | Bugs or comments: labs@nlnetlabs.nl 9 | 10 | To install see the INSTALL instructions file. 11 | 12 | ## Intro 13 | 14 | This package contains the dnssec-trigger tools. It works together with 15 | a local validating resolver (unbound) and keeps DNSSEC enabled. It does 16 | so by selecting DNSSEC enabled upstream caches or servers for unbound 17 | to talk to and by modifying the DNS path on the system to 127.0.0.1. 18 | If DNSSEC does not work because of middleboxes, the insecure option 19 | (after a dialog window for the user) causes the DNS path to be set to 20 | the insecure servers. 21 | 22 | The main components are the daemon, DHCP-hooks, and a GUI-panel. 23 | The daemon starts at bootup and runs in the background. The DHCP hooks 24 | tell the daemon, these are sometimes scripts depending on the system. 25 | The GUI-panel shows a tray icon notification applet. The GUI panel shows 26 | the dialog to the user if insecure is the only option. The GUI panel 27 | has a Reprobe button, so after sigon for the hotspot the user can retry 28 | (it makes the red ! disappear if it works). 29 | 30 | Applications can then trust responses with the AD flag from 127.0.0.1. 31 | But they should know that sometimes the resolv.conf contains 'bad' 32 | insecure servers (not 127.0.0.1) and then they must not trust the AD 33 | flag from them (and may need to send the query without the DO flag 34 | to fallback). Responses asked with DO flag to 127.0.0.1 and with the 35 | returned AD flag can then be trusted. Trusted DNS responses may help 36 | with DANE. 37 | 38 | The dnssec-trigger package thus runs alongside the unbound daemon. It 39 | provides the user with the option to go to Insecure. It selects DNSSEC 40 | service where possible. This helps people run DNSSEC. 41 | 42 | ## Normal usage 43 | 44 | The user logs in and sees a status icon in the tray. Most of the time 45 | it displays no ! (exclamation) but is quiet. The icon can be ignored. 46 | 47 | When the user connects to a new network, the DHCP hooks notify the 48 | dnssec-trigger daemon. This probes the network, and notifies unbound. 49 | The user sees no change and continues to ignore the icon, unless there 50 | is no DNSSEC. 51 | 52 | If the daemon probe fails to find DNSSEC capability, it tells unbound 53 | to stop talking to the network, and tells the statusicon to ask the user. 54 | A dialog pops up out of the tray icon. If insecure, then the resolv.conf 55 | is changed to the insecure servers, unbound is inactive (loops to 56 | 127.0.0.127). The user can work normally on this network connection. 57 | 58 | For a hotspot, the probe would fail (after a second or two), then with 59 | insecure mode the user can login to the hotspot. With Reprobe menu 60 | item the user can reprobe dnssec and if it works then (many hotspots 61 | provide good access once logged in) the icon is restored to safe. The 62 | scripts would also reprobe on a DHCP change. 63 | 64 | 65 | ## Operations on Platforms 66 | 67 | How the different platforms operate is described here. 68 | 69 | ### Security 70 | 71 | There used to be a race condition where DHCP info briefly overriddes 72 | the secure version, but this was fixed in 0.6. 73 | 74 | ### unix - NetworkManager 75 | 76 | In /etc/NetworkManager/dispatcher.d a script sends DHCP changes to 77 | the daemon. The script is a networkmanager dhcp hook script and uses 78 | dnssec-trigger-control to talk to the daemon. The script uses nmcli 79 | to find the DNS info. 80 | 81 | GTK user interface. In /etc/xdg/autostart/ a .desktop entry starts 82 | the user-side tray icon (dnssec-trigger-panel). The daemon is started 83 | from /etc/rc.d like regular daemons. The tray icon communicates with 84 | the daemon over a persistent SSL connection over loopback (127.0.0.1). 85 | It is possible to have multiple tray icons connected over SSL. 86 | 87 | ### unix - Netconfig 88 | 89 | In /etc/netconfig.d a script sends DHCP changes to the daemon. It greps 90 | the info out of /var/run/netconfig/* files. It sends with 91 | dnssec-trigger-control to the daemon. 92 | 93 | GTK like networkmanager. 94 | 95 | ### OSX 96 | 97 | In /Library/LaunchDaemons two plist files exist. One starts the daemon. 98 | The other watches the /Library/Preferences/SystemConfiguration for changes 99 | and launches a script. This script uses ifconfig and parses plist files 100 | and then sends the results with dnssec-trigger-control to the daemon. 101 | 102 | The daemon changes resolv.conf but does not need to as on OSX it also 103 | sets the network preferences for the network interfaces to the values. 104 | These preferences survive a reboot, so the reboot is safe. There then 105 | is no connection until unbound is started during reboot. 106 | 107 | In /Library/LaunchAgents a plist file starts the tray icon (Cocoa app). 108 | It uses an SSL connection to the daemon over loopback (127.0.0.1). 109 | 110 | ### Windows 111 | 112 | The daemon is a service. It has a thread that listens to network changes 113 | and blocks on that, it notifies the main daemon when there is a change. 114 | The DHCP DNS servers are picked from the registry and the override DNS 115 | options are put in the registry as the network preferences. These survive 116 | a reboot, so that the system is safe during a reboot. There then is no 117 | DNS connection until unbound is started during reboot. 118 | 119 | The tray icon is a native application. It uses SSL to talk to the daemon. 120 | 121 | -------------------------------------------------------------------------------- /compat/inet_ntop.c: -------------------------------------------------------------------------------- 1 | /* From openssh 4.3p2 compat/inet_ntop.c */ 2 | /* Copyright (c) 1996 by Internet Software Consortium. 3 | * 4 | * Permission to use, copy, modify, and distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM DISCLAIMS 9 | * ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES 10 | * OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE 11 | * CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL 12 | * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 13 | * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS 14 | * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS 15 | * SOFTWARE. 16 | */ 17 | 18 | /* OPENBSD ORIGINAL: lib/libc/net/inet_ntop.c */ 19 | 20 | #include 21 | 22 | #ifndef HAVE_INET_NTOP 23 | 24 | #include 25 | #include 26 | #ifdef HAVE_SYS_SOCKET_H 27 | #include 28 | #endif 29 | #ifdef HAVE_NETINET_IN_H 30 | #include 31 | #endif 32 | #include 33 | #include 34 | #include 35 | 36 | #ifndef IN6ADDRSZ 37 | #define IN6ADDRSZ 16 /* IPv6 T_AAAA */ 38 | #endif 39 | 40 | #ifndef INT16SZ 41 | #define INT16SZ 2 /* for systems without 16-bit ints */ 42 | #endif 43 | 44 | /* 45 | * WARNING: Don't even consider trying to compile this on a system where 46 | * sizeof(int) < 4. sizeof(int) > 4 is fine; all the world's not a VAX. 47 | */ 48 | 49 | static const char *inet_ntop4(const u_char *src, char *dst, size_t size); 50 | static const char *inet_ntop6(const u_char *src, char *dst, size_t size); 51 | 52 | /* char * 53 | * inet_ntop(af, src, dst, size) 54 | * convert a network format address to presentation format. 55 | * return: 56 | * pointer to presentation format address (`dst'), or NULL (see errno). 57 | * author: 58 | * Paul Vixie, 1996. 59 | */ 60 | const char * 61 | inet_ntop(int af, const void *src, char *dst, size_t size) 62 | { 63 | switch (af) { 64 | case AF_INET: 65 | return (inet_ntop4(src, dst, size)); 66 | case AF_INET6: 67 | return (inet_ntop6(src, dst, size)); 68 | default: 69 | #ifdef EAFNOSUPPORT 70 | errno = EAFNOSUPPORT; 71 | #else 72 | errno = ENOSYS; 73 | #endif 74 | return (NULL); 75 | } 76 | /* NOTREACHED */ 77 | } 78 | 79 | /* const char * 80 | * inet_ntop4(src, dst, size) 81 | * format an IPv4 address, more or less like inet_ntoa() 82 | * return: 83 | * `dst' (as a const) 84 | * notes: 85 | * (1) uses no statics 86 | * (2) takes a u_char* not an in_addr as input 87 | * author: 88 | * Paul Vixie, 1996. 89 | */ 90 | static const char * 91 | inet_ntop4(const u_char *src, char *dst, size_t size) 92 | { 93 | static const char fmt[] = "%u.%u.%u.%u"; 94 | char tmp[sizeof "255.255.255.255"]; 95 | int l; 96 | 97 | l = snprintf(tmp, size, fmt, src[0], src[1], src[2], src[3]); 98 | if (l <= 0 || l >= (int)size) { 99 | errno = ENOSPC; 100 | return (NULL); 101 | } 102 | strlcpy(dst, tmp, size); 103 | return (dst); 104 | } 105 | 106 | /* const char * 107 | * inet_ntop6(src, dst, size) 108 | * convert IPv6 binary address into presentation (printable) format 109 | * author: 110 | * Paul Vixie, 1996. 111 | */ 112 | static const char * 113 | inet_ntop6(const u_char *src, char *dst, size_t size) 114 | { 115 | /* 116 | * Note that int32_t and int16_t need only be "at least" large enough 117 | * to contain a value of the specified size. On some systems, like 118 | * Crays, there is no such thing as an integer variable with 16 bits. 119 | * Keep this in mind if you think this function should have been coded 120 | * to use pointer overlays. All the world's not a VAX. 121 | */ 122 | char tmp[sizeof "ffff:ffff:ffff:ffff:ffff:ffff:255.255.255.255"]; 123 | char *tp, *ep; 124 | struct { int base, len; } best, cur; 125 | u_int words[IN6ADDRSZ / INT16SZ]; 126 | int i; 127 | int advance; 128 | 129 | /* 130 | * Preprocess: 131 | * Copy the input (bytewise) array into a wordwise array. 132 | * Find the longest run of 0x00's in src[] for :: shorthanding. 133 | */ 134 | memset(words, '\0', sizeof words); 135 | for (i = 0; i < IN6ADDRSZ; i++) 136 | words[i / 2] |= (src[i] << ((1 - (i % 2)) << 3)); 137 | best.base = -1; 138 | best.len = 0; 139 | cur.base = -1; 140 | cur.len = 0; 141 | for (i = 0; i < (IN6ADDRSZ / INT16SZ); i++) { 142 | if (words[i] == 0) { 143 | if (cur.base == -1) 144 | cur.base = i, cur.len = 1; 145 | else 146 | cur.len++; 147 | } else { 148 | if (cur.base != -1) { 149 | if (best.base == -1 || cur.len > best.len) 150 | best = cur; 151 | cur.base = -1; 152 | } 153 | } 154 | } 155 | if (cur.base != -1) { 156 | if (best.base == -1 || cur.len > best.len) 157 | best = cur; 158 | } 159 | if (best.base != -1 && best.len < 2) 160 | best.base = -1; 161 | 162 | /* 163 | * Format the result. 164 | */ 165 | tp = tmp; 166 | ep = tmp + sizeof(tmp); 167 | for (i = 0; i < (IN6ADDRSZ / INT16SZ) && tp < ep; i++) { 168 | /* Are we inside the best run of 0x00's? */ 169 | if (best.base != -1 && i >= best.base && 170 | i < (best.base + best.len)) { 171 | if (i == best.base) { 172 | if (tp + 1 >= ep) 173 | return (NULL); 174 | *tp++ = ':'; 175 | } 176 | continue; 177 | } 178 | /* Are we following an initial run of 0x00s or any real hex? */ 179 | if (i != 0) { 180 | if (tp + 1 >= ep) 181 | return (NULL); 182 | *tp++ = ':'; 183 | } 184 | /* Is this address an encapsulated IPv4? */ 185 | if (i == 6 && best.base == 0 && 186 | (best.len == 6 || (best.len == 5 && words[5] == 0xffff))) { 187 | if (!inet_ntop4(src+12, tp, (size_t)(ep - tp))) 188 | return (NULL); 189 | tp += strlen(tp); 190 | break; 191 | } 192 | advance = snprintf(tp, ep - tp, "%x", words[i]); 193 | if (advance <= 0 || advance >= ep - tp) 194 | return (NULL); 195 | tp += advance; 196 | } 197 | /* Was it a trailing run of 0x00's? */ 198 | if (best.base != -1 && (best.base + best.len) == (IN6ADDRSZ / INT16SZ)) { 199 | if (tp + 1 >= ep) 200 | return (NULL); 201 | *tp++ = ':'; 202 | } 203 | if (tp + 1 >= ep) 204 | return (NULL); 205 | *tp++ = '\0'; 206 | 207 | /* 208 | * Check for overflow, copy, and we're done. 209 | */ 210 | if ((size_t)(tp - tmp) > size) { 211 | errno = ENOSPC; 212 | return (NULL); 213 | } 214 | strlcpy(dst, tmp, size); 215 | return (dst); 216 | } 217 | 218 | #endif /* !HAVE_INET_NTOP */ 219 | -------------------------------------------------------------------------------- /compat/inet_pton.c: -------------------------------------------------------------------------------- 1 | /* $KAME: inet_pton.c,v 1.5 2001/08/20 02:32:40 itojun Exp $ */ 2 | 3 | /* Copyright (c) 1996 by Internet Software Consortium. 4 | * 5 | * Permission to use, copy, modify, and distribute this software for any 6 | * purpose with or without fee is hereby granted, provided that the above 7 | * copyright notice and this permission notice appear in all copies. 8 | * 9 | * THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM DISCLAIMS 10 | * ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES 11 | * OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL INTERNET SOFTWARE 12 | * CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL 13 | * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR 14 | * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS 15 | * ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS 16 | * SOFTWARE. 17 | */ 18 | 19 | #include 20 | 21 | #include 22 | #include 23 | #include 24 | 25 | /* 26 | * WARNING: Don't even consider trying to compile this on a system where 27 | * sizeof(int) < 4. sizeof(int) > 4 is fine; all the world's not a VAX. 28 | */ 29 | 30 | static int inet_pton4 (const char *src, uint8_t *dst); 31 | static int inet_pton6 (const char *src, uint8_t *dst); 32 | 33 | /* 34 | * 35 | * The definitions we might miss. 36 | * 37 | */ 38 | #ifndef NS_INT16SZ 39 | #define NS_INT16SZ 2 40 | #endif 41 | 42 | #ifndef NS_IN6ADDRSZ 43 | #define NS_IN6ADDRSZ 16 44 | #endif 45 | 46 | #ifndef NS_INADDRSZ 47 | #define NS_INADDRSZ 4 48 | #endif 49 | 50 | /* int 51 | * inet_pton(af, src, dst) 52 | * convert from presentation format (which usually means ASCII printable) 53 | * to network format (which is usually some kind of binary format). 54 | * return: 55 | * 1 if the address was valid for the specified address family 56 | * 0 if the address wasn't valid (`dst' is untouched in this case) 57 | * -1 if some other error occurred (`dst' is untouched in this case, too) 58 | * author: 59 | * Paul Vixie, 1996. 60 | */ 61 | int 62 | inet_pton(af, src, dst) 63 | int af; 64 | const char *src; 65 | void *dst; 66 | { 67 | switch (af) { 68 | case AF_INET: 69 | return (inet_pton4(src, dst)); 70 | case AF_INET6: 71 | return (inet_pton6(src, dst)); 72 | default: 73 | #ifdef EAFNOSUPPORT 74 | errno = EAFNOSUPPORT; 75 | #else 76 | errno = ENOSYS; 77 | #endif 78 | return (-1); 79 | } 80 | /* NOTREACHED */ 81 | } 82 | 83 | /* int 84 | * inet_pton4(src, dst) 85 | * like inet_aton() but without all the hexadecimal and shorthand. 86 | * return: 87 | * 1 if `src' is a valid dotted quad, else 0. 88 | * notice: 89 | * does not touch `dst' unless it's returning 1. 90 | * author: 91 | * Paul Vixie, 1996. 92 | */ 93 | static int 94 | inet_pton4(src, dst) 95 | const char *src; 96 | uint8_t *dst; 97 | { 98 | static const char digits[] = "0123456789"; 99 | int saw_digit, octets, ch; 100 | uint8_t tmp[NS_INADDRSZ], *tp; 101 | 102 | saw_digit = 0; 103 | octets = 0; 104 | *(tp = tmp) = 0; 105 | while ((ch = *src++) != '\0') { 106 | const char *pch; 107 | 108 | if ((pch = strchr(digits, ch)) != NULL) { 109 | uint32_t new = *tp * 10 + (pch - digits); 110 | 111 | if (new > 255) 112 | return (0); 113 | *tp = new; 114 | if (! saw_digit) { 115 | if (++octets > 4) 116 | return (0); 117 | saw_digit = 1; 118 | } 119 | } else if (ch == '.' && saw_digit) { 120 | if (octets == 4) 121 | return (0); 122 | *++tp = 0; 123 | saw_digit = 0; 124 | } else 125 | return (0); 126 | } 127 | if (octets < 4) 128 | return (0); 129 | 130 | memcpy(dst, tmp, NS_INADDRSZ); 131 | return (1); 132 | } 133 | 134 | /* int 135 | * inet_pton6(src, dst) 136 | * convert presentation level address to network order binary form. 137 | * return: 138 | * 1 if `src' is a valid [RFC1884 2.2] address, else 0. 139 | * notice: 140 | * (1) does not touch `dst' unless it's returning 1. 141 | * (2) :: in a full address is silently ignored. 142 | * credit: 143 | * inspired by Mark Andrews. 144 | * author: 145 | * Paul Vixie, 1996. 146 | */ 147 | static int 148 | inet_pton6(src, dst) 149 | const char *src; 150 | uint8_t *dst; 151 | { 152 | static const char xdigits_l[] = "0123456789abcdef", 153 | xdigits_u[] = "0123456789ABCDEF"; 154 | uint8_t tmp[NS_IN6ADDRSZ], *tp, *endp, *colonp; 155 | const char *xdigits, *curtok; 156 | int ch, saw_xdigit; 157 | uint32_t val; 158 | 159 | memset((tp = tmp), '\0', NS_IN6ADDRSZ); 160 | endp = tp + NS_IN6ADDRSZ; 161 | colonp = NULL; 162 | /* Leading :: requires some special handling. */ 163 | if (*src == ':') 164 | if (*++src != ':') 165 | return (0); 166 | curtok = src; 167 | saw_xdigit = 0; 168 | val = 0; 169 | while ((ch = *src++) != '\0') { 170 | const char *pch; 171 | 172 | if ((pch = strchr((xdigits = xdigits_l), ch)) == NULL) 173 | pch = strchr((xdigits = xdigits_u), ch); 174 | if (pch != NULL) { 175 | val <<= 4; 176 | val |= (pch - xdigits); 177 | if (val > 0xffff) 178 | return (0); 179 | saw_xdigit = 1; 180 | continue; 181 | } 182 | if (ch == ':') { 183 | curtok = src; 184 | if (!saw_xdigit) { 185 | if (colonp) 186 | return (0); 187 | colonp = tp; 188 | continue; 189 | } 190 | if (tp + NS_INT16SZ > endp) 191 | return (0); 192 | *tp++ = (uint8_t) (val >> 8) & 0xff; 193 | *tp++ = (uint8_t) val & 0xff; 194 | saw_xdigit = 0; 195 | val = 0; 196 | continue; 197 | } 198 | if (ch == '.' && ((tp + NS_INADDRSZ) <= endp) && 199 | inet_pton4(curtok, tp) > 0) { 200 | tp += NS_INADDRSZ; 201 | saw_xdigit = 0; 202 | break; /* '\0' was seen by inet_pton4(). */ 203 | } 204 | return (0); 205 | } 206 | if (saw_xdigit) { 207 | if (tp + NS_INT16SZ > endp) 208 | return (0); 209 | *tp++ = (uint8_t) (val >> 8) & 0xff; 210 | *tp++ = (uint8_t) val & 0xff; 211 | } 212 | if (colonp != NULL) { 213 | /* 214 | * Since some memmove()'s erroneously fail to handle 215 | * overlapping regions, we'll do the shift by hand. 216 | */ 217 | const int n = tp - colonp; 218 | int i; 219 | 220 | for (i = 1; i <= n; i++) { 221 | endp[- i] = colonp[n - i]; 222 | colonp[n - i] = 0; 223 | } 224 | tp = endp; 225 | } 226 | if (tp != endp) 227 | return (0); 228 | memcpy(dst, tmp, NS_IN6ADDRSZ); 229 | return (1); 230 | } 231 | -------------------------------------------------------------------------------- /compat/malloc.c: -------------------------------------------------------------------------------- 1 | /* Just a replacement, if the original malloc is not 2 | GNU-compliant. See autoconf documentation. */ 3 | 4 | #include "config.h" 5 | #undef malloc 6 | #include 7 | 8 | void *malloc (); 9 | 10 | /* Allocate an N-byte block of memory from the heap. 11 | If N is zero, allocate a 1-byte block. */ 12 | 13 | void * 14 | rpl_malloc_dnssectrigger (size_t n) 15 | { 16 | if (n == 0) 17 | n = 1; 18 | return malloc (n); 19 | } 20 | -------------------------------------------------------------------------------- /compat/memmove.c: -------------------------------------------------------------------------------- 1 | /* 2 | * memmove.c: memmove compat implementation. 3 | * 4 | * Copyright (c) 2001-2006, NLnet Labs. All rights reserved. 5 | * 6 | * See LICENSE for the license. 7 | */ 8 | 9 | #include 10 | #include 11 | 12 | void *memmove(void *dest, const void *src, size_t n); 13 | 14 | void *memmove(void *dest, const void *src, size_t n) 15 | { 16 | uint8_t* from = (uint8_t*) src; 17 | uint8_t* to = (uint8_t*) dest; 18 | 19 | if (from == to || n == 0) 20 | return dest; 21 | if (to > from && to-from < (int)n) { 22 | /* to overlaps with from */ 23 | /* */ 24 | /* */ 25 | /* copy in reverse, to avoid overwriting from */ 26 | int i; 27 | for(i=n-1; i>=0; i--) 28 | to[i] = from[i]; 29 | return dest; 30 | } 31 | if (from > to && from-to < (int)n) { 32 | /* to overlaps with from */ 33 | /* */ 34 | /* */ 35 | /* copy forwards, to avoid overwriting from */ 36 | size_t i; 37 | for(i=0; i 4 | * 5 | * Permission to use, copy, modify, and distribute this software for any 6 | * purpose with or without fee is hereby granted, provided that the above 7 | * copyright notice and this permission notice appear in all copies. 8 | * 9 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 10 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 11 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 12 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 13 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 14 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 15 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 16 | */ 17 | 18 | /* OPENBSD ORIGINAL: lib/libc/string/strlcpy.c */ 19 | 20 | #include 21 | #ifndef HAVE_STRLCPY 22 | 23 | #include 24 | #include 25 | 26 | /* 27 | * Copy src to string dst of size siz. At most siz-1 characters 28 | * will be copied. Always NUL terminates (unless siz == 0). 29 | * Returns strlen(src); if retval >= siz, truncation occurred. 30 | */ 31 | size_t 32 | strlcpy(char *dst, const char *src, size_t siz) 33 | { 34 | char *d = dst; 35 | const char *s = src; 36 | size_t n = siz; 37 | 38 | /* Copy as many bytes as will fit */ 39 | if (n != 0 && --n != 0) { 40 | do { 41 | if ((*d++ = *s++) == 0) 42 | break; 43 | } while (--n != 0); 44 | } 45 | 46 | /* Not enough room in dst, add NUL and traverse rest of src */ 47 | if (n == 0) { 48 | if (siz != 0) 49 | *d = '\0'; /* NUL-terminate dst */ 50 | while (*s++) 51 | ; 52 | } 53 | 54 | return(s - src - 1); /* count does not include NUL */ 55 | } 56 | 57 | #endif /* !HAVE_STRLCPY */ 58 | -------------------------------------------------------------------------------- /contrib/README: -------------------------------------------------------------------------------- 1 | These files are contributed to dnssec-trigger, and are not part of the official 2 | distribution but may be helpful. 3 | 4 | * dnssec-trigger-script: A python script that reconfigures /etc/resolv.conf, dnssec-trigger and unbound. 5 | * dnssec.conf.sample: A sample /etc/dnssec.conf file used by dnssec-trigger-script. 6 | * 01-dnssec-trigger: A minimalistic NetworkManager dispatcher.d shell script that calls dnssec-trigger-script --update. 7 | -------------------------------------------------------------------------------- /dnssec-trigger-netconfig-hook.sh.in: -------------------------------------------------------------------------------- 1 | #!@SHELL@ 2 | # 3 | # dnssec trigger for netconfig 4 | # if we are in alternate root 5 | r="$ROOT" 6 | 7 | ifconfig="/sbin/ifconfig" 8 | # in files like /var/run/netconfig/eth0/netconfig0 9 | # there is DNSSERVERS='192.168.254.254 192.168.254.254' 10 | netconfdir="$r/var/run/netconfig" 11 | 12 | # see which ifs are up 13 | ifs=`$ifconfig | awk '/^[a-z]/ { sub(/ .*$/,empty); iface=$0 } / UP / { print iface }'` 14 | ifs=`echo $ifs` 15 | logger "dnssec-trigger detected interfaces $ifs" 16 | 17 | # get DNS for ifs 18 | ips="" 19 | for i in $ifs; do 20 | if test -d $netconfdir/$i; then 21 | for f in $netconfdir/$i/*; do 22 | ips_now=`awk "/^DNSSERVERS=/ { sub(/DNSSERVERS='/,\"\"); sub(/'\$/,\"\"); print } " < $f ` 23 | ips="$ips $ips_now" 24 | done; 25 | fi 26 | done 27 | ips=`echo $ips` 28 | 29 | logger "dnssec-trigger(netconfig) detected $ifs DNS $ips" 30 | @sbindir@/dnssec-trigger-control submit "$ips" 31 | exit 0 32 | -------------------------------------------------------------------------------- /dnssec-triggerd-keygen.service: -------------------------------------------------------------------------------- 1 | [Unit] 2 | Description=Generate keys and certificates for dnssec-trigger 3 | ConditionPathExists=!/etc/dnssec-trigger/dnssec_trigger_control.key 4 | 5 | [Service] 6 | Type=oneshot 7 | ExecStart=/usr/sbin/dnssec-trigger-control-setup -d /etc/dnssec-trigger/ 8 | RemainAfterExit=yes 9 | -------------------------------------------------------------------------------- /dnssec-triggerd.service.in: -------------------------------------------------------------------------------- 1 | [Unit] 2 | Description=Reconfigure local DNSSEC resolver on connectivity changes 3 | After=NetworkManager.service unbound.service dnssec-triggerd-keygen.service 4 | Requires=unbound.service 5 | Wants=dnssec-triggerd-keygen.service 6 | 7 | [Service] 8 | PIDFile=@pidfile@ 9 | Type=simple 10 | Restart=always 11 | ExecStart=@sbindir@/dnssec-triggerd -d 12 | ExecStartPre=-@libexecdir@/dnssec-trigger-script --prepare 13 | ExecStartPost=-@libexecdir@/dnssec-trigger-script --@NMDISPATCHERCOMMAND@ 14 | ExecStopPost=-@libexecdir@/dnssec-trigger-script --cleanup 15 | 16 | [Install] 17 | WantedBy=multi-user.target 18 | -------------------------------------------------------------------------------- /dnssec.conf: -------------------------------------------------------------------------------- 1 | # The options configured in this file are supported by dnssec-trigger-script 2 | # which is called due to various events in related services including 3 | # dnssec-trigger and NetworkManager. As a result, dnssec-trigger-script, 4 | # together with the dnssec-trigger daemon, reconfigures a running instance 5 | # of Unbound, your local validating resolver. 6 | # 7 | # Changes in this file are typically applied on the next network change. To 8 | # make them work immediately, restart the dnssec-trigger service. On many 9 | # systems this is achieved by the following command: 10 | # 11 | # systemctl restart dnssec-triggerd 12 | # 13 | # To achieve a clean state of Unbound, you can just restart the unbound 14 | # service and dnssec-trigger gets restarted automatically. Note that some 15 | # other services like VPN clients may have reconfigured unbound at runtime 16 | # and thus may need to be restarted as well. 17 | # 18 | # systemctl restart unbound 19 | # 20 | # In future some of the options may be interpretted by other services as well, 21 | # so be careful to restart all of them. One such service may be a future 22 | # version of NetworkManager. 23 | # 24 | # systemctl restart NetworkManager 25 | # 26 | 27 | # validate_connection_provided_zones: 28 | # ----------------------------------- 29 | # Ensures that foward zones provided by NetworkManager connections will be 30 | # validated by Unbound. 31 | # 32 | # Security notes: 33 | # 34 | # - If this option is turned off, the network you're connecting to 35 | # can provide you a list of spoofed domains e.g. via DHCP. Those domains 36 | # are then configured as insecure forward zones in your local validating 37 | # resolver, constituting a downgrade attack on DNSSEC validation. 38 | # 39 | # - See also security notes on the `add_wifi_provided_zones` option. 40 | # 41 | # validate_connection_provided_zones=yes 42 | # 43 | # - Connection provided zones will be configured in Unbound as secure forward 44 | # zones, validated using DNSSEC. 45 | # 46 | # If the DNS servers for such a connection are not capable of forwarding 47 | # DNSSEC queries and responses or the local zone is required to be signed 48 | # according to the global DNSSEC database, local resources will not be 49 | # resolved correctly and will appear inaccessible. 50 | # 51 | # Many networks use fake top level domains which fail DNSSEC validation 52 | # as there is no way to validate them at all. Do not use this strict 53 | # option if you want to access resources on such networks. 54 | # 55 | # validate_connection_provided_zones=no 56 | # 57 | # - Connection provided zones will be configured in Unbound as insecure 58 | # forward zones, not validated using DNSSEC. This allows you to access 59 | # local resources on networks with non-compliant DNS servers as well 60 | # as networks that hijack domains that are either not in the global DNS 61 | # tree at all or are required to be signed. 62 | # 63 | # Turning this option off has security implications, See the security 64 | # notice above. 65 | # 66 | validate_connection_provided_zones=yes 67 | 68 | # add_wifi_provided_zones: 69 | # ------------------------ 70 | # Ensures that wifi provided zones are accepted by dnssec-trigger-script just 71 | # as any other connection provided zones. Wireless ethernet is special in 72 | # that you often connect to network with no authentication or authentication 73 | # based on a shared secret. 74 | # 75 | # Security notes: 76 | # 77 | # - Anyone knowing such a shared secret can set up an access point for the 78 | # network and provide you a spoofed domain list via DHCP. When this option 79 | # is turned on, the spoofed domains are configured as forward zones in your 80 | # local validating resolver. 81 | # 82 | # - See also security notes on the `validate_connection_provided_zones` option. 83 | # 84 | # add_wifi_provided_zones=yes 85 | # 86 | # - Domains provided by WiFi connections will be configured as forward zones 87 | # in your local validating resolver. See the security notice above. 88 | # 89 | # add_wifi_provided_zones=no 90 | # 91 | # - Domains provided by WiFi connection will be ignored. 92 | # 93 | add_wifi_provided_zones=no 94 | 95 | # set_search_domains: 96 | # ------------------- 97 | # Enable or disable writing of search domains to `/etc/resolv.conf`. 98 | # 99 | # set_search_domains=yes - Search domains are written to `/etc/resolv.conf`. 100 | # 101 | # set_search_domains=no - Search domains are not written to `/etc/resolv.conf`. 102 | # 103 | set_search_domains=no 104 | 105 | # use_private_address_ranges: 106 | # --------------------------- 107 | # Enable or disable adding reverse name resolution zones derived from 108 | # private IP addresses as defined in RFC 1918 and RFC 4193. 109 | # 110 | # use_private_address_ranges=yes - Use standard private IP address ranges to build 111 | # reverse name resolution zones using the global 112 | # forwarders. 113 | # 114 | # use_private_address_ranges=no - Ignore standard IP address ranges. 115 | use_private_address_ranges=yes 116 | -------------------------------------------------------------------------------- /example.conf.in: -------------------------------------------------------------------------------- 1 | # config for dnssec-trigger @VERSION@. 2 | # this is a comment. there must be one statement per line. 3 | 4 | # logging detail, 0=only errors, 1=operations, 2=detail, 3,4 debug detail. 5 | # verbosity: 1 6 | 7 | # pidfile location 8 | # pidfile: "@pidfile@" 9 | 10 | # log to a file instead of syslog, default is to syslog 11 | # logfile: "/var/log/dnssec-trigger.log" 12 | 13 | # log to syslog, or (log to to stderr or a logfile if specified). yes or no. 14 | # use-syslog: yes 15 | 16 | # chroot to this directory 17 | # chroot: "" 18 | 19 | # the unbound-control binary if not found in PATH. 20 | # commandline options can be appended "unbound-control -c my.conf" if you wish. 21 | # unbound-control: "@unbound_control_path@" 22 | 23 | # where is resolv.conf to edit. 24 | # resolvconf: "/etc/resolv.conf" 25 | 26 | # the domain example.com line (if any) to add to resolv.conf(5). default none. 27 | # domain: "" 28 | 29 | # domain name search path to add to resolv.conf(5). default none. 30 | # the search path from DHCP is not picked up, it could be used to misdirect. 31 | # search: "" 32 | 33 | # the command to run to open login pages on hot spots, a web browser. 34 | # empty string runs no command. 35 | # login-command: "@login_command@" 36 | 37 | # the url to open to get hot spot login, it gets overridden by the hotspot. 38 | # login-location: "@login_location@" 39 | 40 | # do not perform actions (unbound-control or resolv.conf), for a dry-run. 41 | # noaction: no 42 | 43 | # port number to use for probe daemon. 44 | # port: 8955 45 | 46 | # these keys and certificates can be generated with the script 47 | # dnssec-trigger-control-setup 48 | # server-key-file: "@keydir@/dnssec_trigger_server.key" 49 | # server-cert-file: "@keydir@/dnssec_trigger_server.pem" 50 | # control-key-file: "@keydir@/dnssec_trigger_control.key" 51 | # control-cert-file: "@keydir@/dnssec_trigger_control.pem" 52 | 53 | # check for updates, download and ask to install them (for Windows, OSX). 54 | # check-updates: @check_updates@ 55 | 56 | # webservers that are probed to see if internet access is possible. 57 | # They serve a simple static page over HTTP port 80. It probes a random url: 58 | # after a space is the content expected on the page, (the page can contain 59 | # whitespace before and after this code). Without urls it skips http probes. 60 | 61 | # provided by NLnetLabs 62 | # It is provided on a best effort basis, with no service guarantee. 63 | url: "http://ster.nlnetlabs.nl/hotspot.txt OK" 64 | 65 | # provided by FedoraProject 66 | url: "http://fedoraproject.org/static/hotspot.txt OK" 67 | 68 | # fallback open DNSSEC resolvers that run on TCP port 80 and TCP port 443. 69 | # These relay incoming DNS traffic on the other port numbers to the usual DNS 70 | # the ssl443 adds an ssl server IP, you may also specify one or more hashes 71 | # the following on one line: ssl443:{} 72 | # hash is output of openssl x509 -sha256 -fingerprint -in server.pem 73 | # You can add more with extra config lines. 74 | 75 | # provided by NLnetLabs 76 | # It is provided on a best effort basis, with no service guarantee. 77 | tcp80: 185.49.140.67 78 | tcp80: 2a04:b900::10:0:0:67 79 | ssl443: 185.49.140.67 7E:CF:B4:BE:B9:9A:56:0D:F7:3B:40:51:A4:78:E6:A6:FD:66:0F:10:58:DC:A8:2E:C0:43:D4:77:5A:71:8A:CF 80 | ssl443: 2a04:b900::10:0:0:67 7E:CF:B4:BE:B9:9A:56:0D:F7:3B:40:51:A4:78:E6:A6:FD:66:0F:10:58:DC:A8:2E:C0:43:D4:77:5A:71:8A:CF 81 | 82 | # Use VPN servers for all traffic 83 | # use-vpn-forwarders: no 84 | 85 | # Forward RFC 1918 private addresses to global forwarders 86 | # use-private-addresses: yes 87 | 88 | # Add domains provided by VPN connections into Unbound forward zones 89 | # add-wifi-provided-zones: no 90 | 91 | -------------------------------------------------------------------------------- /fedora/tmpfiles-unbound.conf: -------------------------------------------------------------------------------- 1 | D /var/run/unbound 0755 unbound unbound - 2 | -------------------------------------------------------------------------------- /fedora/unbound-keygen.service: -------------------------------------------------------------------------------- 1 | [Unit] 2 | Description=Unbound Control Key And Certificate Generator 3 | After=syslog.target 4 | Before=unbound.service 5 | ConditionPathExists=!/etc/unbound/unbound_control.key 6 | 7 | [Service] 8 | Type=oneshot 9 | Group=unbound 10 | ExecStart=/usr/sbin/unbound-control-setup -d /etc/unbound/ 11 | ExecStart=/sbin/restorecon /etc/unbound/* 12 | RemainAfterExit=yes 13 | 14 | [Install] 15 | WantedBy=multi-user.target 16 | -------------------------------------------------------------------------------- /fedora/unbound.service: -------------------------------------------------------------------------------- 1 | [Unit] 2 | Description=Unbound recursive Domain Name Server 3 | After=syslog.target network.target 4 | After=unbound-keygen.service 5 | Wants=unbound-keygen.service 6 | 7 | [Service] 8 | Type=forking 9 | PIDFile=/var/run/unbound/unbound.pid 10 | EnvironmentFile=-/etc/sysconfig/unbound 11 | ExecStart=/usr/sbin/unbound 12 | 13 | [Install] 14 | WantedBy=multi-user.target 15 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/English.lproj/InfoPlist.strings: -------------------------------------------------------------------------------- 1 | /* Localized versions of Info.plist keys */ 2 | 3 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/RiggerApp.h: -------------------------------------------------------------------------------- 1 | // 2 | // RiggerApp.h 3 | // RiggerStatusItem 4 | // 5 | // Created by Wouter Wijngaards on 8/29/11. 6 | // Copyright 2011 NLnet Labs. All rights reserved. 7 | // 8 | 9 | #import 10 | struct cfg; 11 | 12 | /* class that helps catch window close on the noweb window */ 13 | @interface NowebDelegate : NSObject { 14 | } 15 | -(BOOL)windowShouldClose:(NSWindow*)sender; 16 | @end 17 | 18 | /* class that helps catch window close on the update window */ 19 | @interface UpdateDelegate : NSObject { 20 | } 21 | -(BOOL)windowShouldClose:(NSWindow*)sender; 22 | @end 23 | 24 | 25 | @interface RiggerApp : NSObject { 26 | /* outlets connect to the interface */ 27 | IBOutlet NSMenu* riggermenu; 28 | NSStatusItem* riggeritem; 29 | NSImage* icon; 30 | NSImage* icon_alert; 31 | IBOutlet NSWindow* resultwindow; 32 | IBOutlet NSTextView* resultpane; 33 | IBOutlet NSWindow* unsafewindow; 34 | IBOutlet NSTextField* unsafepane; 35 | IBOutlet NSWindow* hotsignwindow; 36 | IBOutlet NSWindow* nowebwindow; 37 | IBOutlet NSWindow* updatewindow; 38 | IBOutlet NSTextField* updatelabel; 39 | 40 | @public 41 | /** if we have asked about disconnect or insecure */ 42 | int unsafe_asked; 43 | /** if we should ask unsafe */ 44 | int unsafe_should; 45 | /** if we have asked about noweb access */ 46 | int noweb_asked; 47 | /** configuration */ 48 | struct cfg* cfg; 49 | } 50 | 51 | /* IBAction to connect to the routine that takes actions after menu */ 52 | -(IBAction)Reprobe:(id)sender; 53 | -(IBAction)ProbeResults:(id)sender; 54 | -(IBAction)ProbeResultsOK:(id)sender; 55 | -(IBAction)UnsafeInsecure:(id)sender; 56 | -(IBAction)UnsafeDisconnect:(id)sender; 57 | -(IBAction)HotspotSignon:(id)sender; 58 | -(IBAction)HotsignOK:(id)sender; 59 | -(IBAction)HotsignCancel:(id)sender; 60 | -(IBAction)NowebLogin:(id)sender; 61 | -(IBAction)NowebSkip:(id)sender; 62 | -(IBAction)UpdateOK:(id)sender; 63 | -(IBAction)UpdateCancel:(id)sender; 64 | -(BOOL)windowShouldClose:(NSWindow*)sender; 65 | -(void)SpawnFeed:(id)param; 66 | -(void)PanelUpdateAlert; 67 | -(void)PanelAlert; 68 | -(void)PresentUnsafeDialog; 69 | -(void)PanelAlertDanger; 70 | -(void)PanelAlertSafe; 71 | -(void)PresentNowebDialog; 72 | -(void)PresentUpdateDialog:(char*)newversion; 73 | 74 | @end 75 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/RiggerStatusItem-Info.plist: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | CFBundleDevelopmentRegion 6 | English 7 | CFBundleExecutable 8 | ${EXECUTABLE_NAME} 9 | CFBundleIconFile 10 | 11 | CFBundleIdentifier 12 | com.yourcompany.${PRODUCT_NAME:rfc1034identifier} 13 | CFBundleInfoDictionaryVersion 14 | 6.0 15 | CFBundleName 16 | ${PRODUCT_NAME} 17 | CFBundlePackageType 18 | APPL 19 | CFBundleSignature 20 | ???? 21 | CFBundleShortVersionString 22 | 1.0 23 | LSMinimumSystemVersion 24 | ${MACOSX_DEPLOYMENT_TARGET} 25 | CFBundleVersion 26 | 1 27 | NSMainNibFile 28 | MainMenu 29 | NSPrincipalClass 30 | NSApplication 31 | LSUIElement 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/RiggerStatusItemAppDelegate.h: -------------------------------------------------------------------------------- 1 | // 2 | // RiggerStatusItemAppDelegate.h 3 | // RiggerStatusItem 4 | // 5 | // Created by Wouter Wijngaards on 8/29/11. 6 | // Copyright 2011 NLnet Labs. All rights reserved. 7 | // 8 | 9 | #import 10 | 11 | @interface RiggerStatusItemAppDelegate : NSObject { 12 | NSWindow *window; 13 | } 14 | 15 | @property (assign) IBOutlet NSWindow *window; 16 | 17 | @end 18 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/RiggerStatusItemAppDelegate.m: -------------------------------------------------------------------------------- 1 | // 2 | // RiggerStatusItemAppDelegate.m 3 | // RiggerStatusItem 4 | // 5 | // Created by Wouter Wijngaards on 8/29/11. 6 | // Copyright 2011 NLnet Labs. All rights reserved. 7 | // 8 | 9 | #import "RiggerStatusItemAppDelegate.h" 10 | 11 | @implementation RiggerStatusItemAppDelegate 12 | 13 | @synthesize window; 14 | 15 | - (void)applicationDidFinishLaunching:(NSNotification *)aNotification { 16 | // Insert code here to initialize your application 17 | } 18 | 19 | @end 20 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/RiggerStatusItem_Prefix.pch: -------------------------------------------------------------------------------- 1 | // 2 | // Prefix header for all source files of the 'RiggerStatusItem' target in the 'RiggerStatusItem' project 3 | // 4 | 5 | #ifdef __OBJC__ 6 | #import 7 | #endif 8 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/main.m: -------------------------------------------------------------------------------- 1 | // 2 | // main.m 3 | // RiggerStatusItem 4 | // 5 | // Created by Wouter Wijngaards on 8/29/11. 6 | // Copyright 2011 NLnet Labs. All rights reserved. 7 | // 8 | 9 | #import 10 | char* test_config_file = NULL; 11 | 12 | int main(int argc, char *argv[]) 13 | { 14 | if(argc > 2 && strcmp(argv[1], "-c") == 0) { 15 | test_config_file = argv[2]; 16 | argv[2] = argv[0]; 17 | argv += 2; 18 | argc -= 2; 19 | } 20 | return NSApplicationMain(argc, (const char **) argv); 21 | } 22 | -------------------------------------------------------------------------------- /osx/RiggerStatusItem/status-icon-alert.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/osx/RiggerStatusItem/status-icon-alert.png -------------------------------------------------------------------------------- /osx/RiggerStatusItem/status-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/osx/RiggerStatusItem/status-icon.png -------------------------------------------------------------------------------- /osx/dnssec-trigger-osx.sh.in: -------------------------------------------------------------------------------- 1 | #!@SHELL@ 2 | # 3 | # dnssec trigger for OSX 4 | 5 | # the network state has changed, obtain a list of DHCP provided DNS servers. 6 | # somehow in /Library/Preferences/SystemConfiguration/ 7 | # com.apple.network.identification.plist - list of configs seen 8 | # preferences.plist - list of what is entered in the config panel 9 | tempfile=/tmp/dnssec-trigger-osx.tmp 10 | 11 | # active interfaces 12 | ifs=`ifconfig | awk '/^[^ :]*:/ { sub(/:.*$/,empty); iface=$0 } /status: active/ { print iface }'` 13 | ifs=`echo $ifs` 14 | 15 | # the ssid(s) of the wifi 16 | ssid=`/System/Library/PrivateFrameworks/Apple80211.framework/Versions/A/Resources/airport -I 2>&1 | grep "[^B]SSID:"` 17 | bssid=`/System/Library/PrivateFrameworks/Apple80211.framework/Versions/A/Resources/airport -I 2>&1 | grep "BSSID:"` 18 | 19 | # and the DNS servers for that 20 | ips="" 21 | for i in $ifs; do 22 | ips_i=`ipconfig getpacket $i | grep "domain_name_server" | sed -e 's/^.*{//' -e 's/,/ /g' -e 's/}//' ` 23 | ips="$ips $ips_i" 24 | done 25 | # fix whitespace 26 | ips=`echo $ips` 27 | 28 | # see if it has changed 29 | if test -f $tempfile; then 30 | if echo "$ifs $ips $ssid $bssid" | diff $tempfile - >/dev/null; then 31 | # it is equal 32 | #logger "dnssec-trigger(osx) no-change $ifs DNS $ips" 33 | exit 0 34 | fi 35 | fi 36 | # store on file 37 | echo "$ifs $ips $ssid $bssid" > $tempfile 38 | 39 | logger "dnssec-trigger(osx) detected $ifs DNS $ips" 40 | @sbindir@/dnssec-trigger-control submit "$ips" 41 | exit 0 42 | -------------------------------------------------------------------------------- /osx/dnssec-trigger-setdns.sh.in: -------------------------------------------------------------------------------- 1 | #!@SHELL@ 2 | # dnssec-trigger shell script to set DNS servers on OSX. 3 | # must run as root. 4 | # 5 | # usage: set example.com 192.0.2.1 192.0.2.2 6 | 7 | # perform software upgrade install 8 | function doinstall () { 9 | dmg="$*" 10 | mnt="/tmp/installdir.$$" 11 | logger "start setdns install" 12 | # copy the dmg to a tempfile because the hdiutil needs exclusive access 13 | cp $dmg $dmg.$$ 14 | for (( try=0 ; try <= 20 ; try++ )) ; do 15 | hdiutil attach "$dmg.$$" -mountpoint "$mnt" -nobrowse -noautoopen -noverify 16 | if test $? = 0 ; then 17 | # it worked 18 | break 19 | fi 20 | sleep 1 21 | done 22 | logger "mounted setdns install" 23 | # run the installer from mnt/dnssectrigger-x.x-i386.mpkg 24 | pkg="`ls -d $mnt/dnssectrigger-*.mpkg`" 25 | installer -pkg "$pkg" -target / 26 | logger "done installer setdns install" 27 | hdiutil detach "$mnt" -force 28 | logger "detached setdns install" 29 | rm -f $dmg $dmg.$$ 30 | } 31 | 32 | cmd="$1" 33 | shift 34 | if test "$cmd" = "set"; then 35 | domains="$1" 36 | firstdomain="$1" 37 | shift 38 | # remaining arguments are the servers to set 39 | servers="$*" 40 | logger "dnssec-trigger-setdns to $domains and $servers" 41 | elif test "$cmd" = "mset"; then 42 | domains="$1" 43 | firstdomain="$1" 44 | shift 45 | while test "$1" != "--"; do 46 | domains="$domains $1" 47 | shift 48 | done 49 | if test "$1" != "--"; then 50 | echo >&2 "Usage: $0 mset domain [domain ..] -- server [server ..]" 51 | exit 1 52 | fi 53 | shift # -- 54 | servers="$*" 55 | logger "dnssec-trigger-setdns to $domains and $servers" 56 | elif test "$cmd" = "install"; then 57 | doinstall "$*" 58 | exit 0 59 | else 60 | if test "$cmd" = "uninit"; then 61 | logger "dnssec-trigger-setdns uninit dns override" 62 | else 63 | echo >&2 "bad command: set | mset | uninit" 64 | echo >&2 " set domain [ip ..]" 65 | echo >&2 " mset domain [domain ..] -- ip [ip ..]" 66 | exit 1 67 | fi 68 | firstdomain="" 69 | domains="" 70 | servers="" 71 | fi 72 | 73 | # sets the DNS settings via scutil. 74 | function with_scutil () { 75 | # find the ids of the networkservices that are running or important 76 | # output like: State:/Network/Service/AB5ED934-29E2-4E1B-BEDC-9167410B49A0/DNS 77 | ids=`echo "list State:/Network/Service/[^/]+/DNS" | scutil | sed -e "s?^.* = ??"` 78 | # set the nameservers of all those entries (and the global one) 79 | for i in $ids State:/Network/Global/DNS; do 80 | scutil </dev/null | grep -v '*' | while read x ; do 101 | #echo $x 102 | $nws -setsearchdomains "$x" $domains 103 | # no quotes around servers: the IPs have to be separate arguments. 104 | $nws -setdnsservers "$x" $servers 105 | done 106 | 107 | -------------------------------------------------------------------------------- /osx/nl.nlnetlabs.dnssec-trigger-hook.plist.in: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | Label 7 | nl.nlnetlabs.dnssec-trigger-hook 8 | ProgramArguments 9 | 10 | @libexecdir@/dnssec-trigger-osx.sh 11 | 12 | WatchPaths 13 | 14 | /Library/Preferences/SystemConfiguration 15 | 16 | ThrottleInterval 17 | 1 18 | 19 | 20 | -------------------------------------------------------------------------------- /osx/nl.nlnetlabs.dnssec-trigger-panel.plist.in: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | KeepAlive 7 | 8 | Label 9 | nl.nlnetlabs.dnssec-trigger-panel 10 | ProgramArguments 11 | 12 | @libexecdir@/RiggerStatusItem.app/Contents/MacOS/RiggerStatusItem 13 | 14 | 15 | 16 | -------------------------------------------------------------------------------- /osx/nl.nlnetlabs.dnssec-triggerd.plist.in: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 9 | 10 | Label 11 | nl.nlnetlabs.dnssec-triggerd 12 | 13 | ProgramArguments 14 | 15 | @sbindir@/dnssec-triggerd 16 | -d 17 | 18 | 19 | UserName 20 | root 21 | 22 | RunAtLoad 23 | 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /osx/pkg/dmg-template.dmg.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/osx/pkg/dmg-template.dmg.gz -------------------------------------------------------------------------------- /osx/pkg/package-bg.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/osx/pkg/package-bg.png -------------------------------------------------------------------------------- /osx/wakelist.h: -------------------------------------------------------------------------------- 1 | /* 2 | * wakelist.h - dnssec-trigger OSX sleep and wake listener. 3 | * 4 | * Copyright (c) 2013, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains the OSX sleep and wakeup listener service. 40 | */ 41 | 42 | #ifndef OSX_WAKELIST_H 43 | #define OSX_WAKELIST_H 44 | struct svr; 45 | 46 | /** 47 | * Start the wake and sleep listener thread 48 | * @param cfg: the configuration to know how to kick unbound's cache. 49 | * config is copied, for threadsafe access. 50 | */ 51 | void osx_wakelistener_start(struct cfg* cfg); 52 | 53 | #endif /* OSX_WAKELIST_H */ 54 | -------------------------------------------------------------------------------- /panel/attach.h: -------------------------------------------------------------------------------- 1 | /* 2 | * attach.h - dnssec-trigger acttachment from panel to daemon. 3 | * 4 | * Copyright (c) 2011, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains the code that attaches the panel to the daemon. 40 | */ 41 | 42 | #ifndef ATTACH_H 43 | #define ATTACH_H 44 | struct feed; 45 | struct cfg; 46 | struct strlist; 47 | 48 | /** attachment structure for the results read thread */ 49 | extern struct feed* feed; 50 | 51 | /** 52 | * Alert arguments 53 | */ 54 | struct alert_arg { 55 | int last_insecure; 56 | int now_insecure; 57 | int now_dark; 58 | int now_cache; 59 | int now_auth; 60 | int now_disconn; 61 | int now_tcp; 62 | int now_ssl; 63 | int now_forced_insecure; 64 | int now_http_insecure; 65 | }; 66 | 67 | /** structure for reading from the daemon */ 68 | struct feed { 69 | /* routine that locks a mutex for this structure */ 70 | void (*lock)(void); 71 | /* routine that unlocks the mutex for this structure */ 72 | void (*unlock)(void); 73 | /* quit the program, when stop is sent by triggerd */ 74 | void (*quit)(void); 75 | /* alert function, new status information */ 76 | void (*alert)(struct alert_arg*); 77 | /* update_alert function, new software update info, must free 78 | * the passed (malloced) version string. */ 79 | void (*update_alert)(char*); 80 | 81 | /* if connection with the daemon has been established. */ 82 | int connected; 83 | /* non connection reason */ 84 | char connect_reason[512]; 85 | 86 | /* list of lines, last has status */ 87 | struct strlist* results, *results_last; 88 | /* if we are in insecure mode - here to see if it has changed */ 89 | int insecure_mode; 90 | 91 | /* list of lines for update status */ 92 | struct strlist* update, *update_last; 93 | 94 | /* config */ 95 | struct cfg* cfg; 96 | /* ssl context with keys */ 97 | SSL_CTX* ctx; 98 | /* ssl to read results from */ 99 | SSL* ssl_read; 100 | /* ssl to write results to */ 101 | SSL* ssl_write; 102 | }; 103 | 104 | /** create the feed structure and inits it 105 | * setups the global feed pointer. 106 | * Then you the caller must fill the function pointers in the struct 107 | * with proper callbacks. Then call attach_start from a fresh thread. 108 | */ 109 | void attach_create(void); 110 | 111 | /** delete feed structure. 112 | */ 113 | void attach_delete(void); 114 | 115 | /** start the connection thread */ 116 | void attach_start(struct cfg* cfg); 117 | 118 | /** stop attach */ 119 | void attach_stop(void); 120 | 121 | /** send insecure choice to the daemon */ 122 | void attach_send_insecure(int val); 123 | void attach_send_reprobe(void); 124 | void attach_send_hotspot_signon(void); 125 | void attach_send_skip_http(void); 126 | void attach_send_update_cancel(void); 127 | void attach_send_update_ok(void); 128 | 129 | /** get tooltip text from alert state (fixed string) */ 130 | const char* state_tooltip(struct alert_arg* a); 131 | /** 132 | * process state for new alert (at GUI side) 133 | * @param a: the alert state info. 134 | * @param unsafe_asked: 1 if user chose something in the unsafe dialog. 135 | * @param noweb_asked: 1 if user chose something in the noweb dialog. 136 | * @param danger: routine to show danger icon 137 | * @param safe: routine to show safe icon. 138 | * @param dialog: routine to show the insecure-question dialog. 139 | * @param noweb: routine to whot the noweb-login dialog. 140 | */ 141 | void process_state(struct alert_arg* a, int* unsafe_asked, int* noweb_asked, 142 | void (*danger)(void), void(*safe)(void), void(*dialog)(void), 143 | void (*noweb)(void)); 144 | 145 | /** 146 | * Fetch proberesults text. 147 | * @param buf: buffer for string. 148 | * @param len: length of buffer. 149 | * @param lf: line ending (string), e.g. "\n" 150 | */ 151 | void fetch_proberesults(char* buf, size_t len, const char* lf); 152 | 153 | /** 154 | * forkexec login command given cfg, where forkexec exists (unix) 155 | * Takes cfg item from feed global. logs errors to syslog. 156 | */ 157 | void run_login(void); 158 | 159 | #endif /* ATTACH_H */ 160 | -------------------------------------------------------------------------------- /panel/dmg-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/panel/dmg-icon.png -------------------------------------------------------------------------------- /panel/dnssec-trigger-panel.desktop.in: -------------------------------------------------------------------------------- 1 | [Desktop Entry] 2 | Type=Application 3 | # note this is the version of the .desktop spec this file conforms to 4 | Version=1.0 5 | Name=DNSSEC Trigger 6 | GenericName=Network Applet 7 | Comment=Shows DNS state and warning dialog 8 | Exec=dnssec-trigger-panel 9 | Icon=@uidir@/status-icon.png 10 | Terminal=false 11 | Categories=Utility; 12 | X-KDE-StartupNotify=false 13 | StartupNotify=false 14 | 15 | -------------------------------------------------------------------------------- /panel/install-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/panel/install-icon.png -------------------------------------------------------------------------------- /panel/status-icon-alert.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/panel/status-icon-alert.png -------------------------------------------------------------------------------- /panel/status-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/panel/status-icon.png -------------------------------------------------------------------------------- /panel/uninstall-icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/panel/uninstall-icon.png -------------------------------------------------------------------------------- /riggerd/connection_list.h: -------------------------------------------------------------------------------- 1 | #if !defined CONNECTION_LIST_H && defined FWD_ZONES_SUPPORT 2 | #define CONNECTION_LIST_H 3 | 4 | #include 5 | #include 6 | 7 | #include "string_list.h" 8 | #include "string_buffer.h" 9 | 10 | /** 11 | * All possible types of connections 12 | * in Network Manager. 13 | */ 14 | enum nm_connection_type { 15 | NM_CON_VPN, 16 | NM_CON_WIFI, 17 | NM_CON_OTHER, 18 | NM_CON_IGNORE, 19 | NM_CON_DELIMITER // XXX: What is this?? 20 | }; 21 | 22 | enum nm_connection_security { 23 | NM_CON_SECURE, 24 | NM_CON_INSECURE, 25 | NM_CON_NA, // <- Not applicable 26 | }; 27 | 28 | /** 29 | * 30 | */ 31 | enum list_ownership_type { 32 | LIST_OWNING, 33 | LIST_NON_OWNING 34 | }; 35 | 36 | /** 37 | * "connection" refers to the concept used by 38 | * NetworkManager. e.g. `$ nmcli con show --active` 39 | */ 40 | struct nm_connection { 41 | /** Is this connection the default one? */ 42 | bool default_con; 43 | /** Linked list of zones */ 44 | struct string_list zones; 45 | /** Type of this connection as defined in enum connection_type */ 46 | enum nm_connection_type type; 47 | /** Linked list of servers */ 48 | struct string_list servers; 49 | /** Marker of secure/insecure connections */ 50 | enum nm_connection_security security; 51 | }; 52 | 53 | /** 54 | * One node of a list of connections 55 | */ 56 | struct nm_connection_node { 57 | /** Pointer to this connection struct. */ 58 | struct nm_connection *self; 59 | /** Pointer to the next connection. */ 60 | struct nm_connection_node *next; 61 | }; 62 | 63 | 64 | /** 65 | * Linked list of connections. 66 | * XXX: ?All nodes and its content is owned by this struct. 67 | */ 68 | struct nm_connection_list { 69 | /** Head of a list */ 70 | struct nm_connection_node *first; 71 | /** Ownership status of this list */ 72 | enum list_ownership_type ownership; 73 | }; 74 | 75 | /** 76 | * Filter function footprint. 77 | * @param conn: The connection struct to check 78 | */ 79 | typedef bool (*filter_conn_fcn)(struct nm_connection const *); 80 | 81 | /** 82 | * Initialize all members of connection struct 83 | * @param conn: Connection to be initialized 84 | */ 85 | void nm_connection_init(struct nm_connection *conn); 86 | 87 | /** 88 | * Free all memory used by this struct 89 | * @param conn: Connection to be freed 90 | */ 91 | void nm_connection_clear(struct nm_connection *conn); 92 | 93 | /* 94 | * Initialize an empty owning list of connections 95 | * @param list: List to be initialized 96 | */ 97 | void nm_connection_list_init(struct nm_connection_list *list); 98 | 99 | /* 100 | * Initialize an empty non-owning list of connections 101 | * @param list: List to be initialized 102 | */ 103 | void nm_connection_list_init_non_owning(struct nm_connection_list *list); 104 | 105 | /** 106 | * Free the whole list and all its components (connection nodes and lists of strings) 107 | * Be careful though, use this only on owning lists. Usage on non-owning lists can cause 108 | * memory corruption. 109 | * @param list: List to be freed 110 | */ 111 | void nm_connection_list_clear(struct nm_connection_list *list); 112 | 113 | /** 114 | * Push a new connections into the list. The new connection is now owned by the list. You 115 | * should not use it elsewhere. 116 | * @param list: List to push to 117 | * @param new_value: New connection 118 | */ 119 | void nm_connection_list_push_back(struct nm_connection_list *list, struct nm_connection *new_value); 120 | 121 | /** 122 | * Copy the new_value and then push it back 123 | * @param list: List to push to 124 | * @param new_value: New connection 125 | */ 126 | void nm_connection_list_copy_and_push_back(struct nm_connection_list *list, struct nm_connection *new_value); 127 | 128 | 129 | /** 130 | * Search for a zone with given name and return if it is present or not 131 | * @param list: List to search through 132 | * @param zone: Zone name 133 | * @param len: Zone name length 134 | */ 135 | bool nm_connection_list_contains_zone(const struct nm_connection_list *list, char *zone, size_t len); 136 | 137 | /** 138 | * Remove the first connection with given zone 139 | * @param list: List to search through 140 | * @param zone: Zone name 141 | * @param len: Zone name length 142 | */ 143 | int nm_connection_list_remove(struct nm_connection_list *list, char *zone, size_t len); 144 | 145 | /** 146 | * 147 | * @param list: List to search through 148 | */ 149 | struct string_list nm_connection_list_get_servers_list(struct nm_connection_list *list); 150 | 151 | /** 152 | * Filter connections list and return a new non-owning one, which contains only those connections 153 | * that satisfy **all** filters. 154 | * @param list: Original list (will be a superset to the new one) 155 | * @param count: Number of filters given to this function 156 | * @return: The new list 157 | */ 158 | struct nm_connection_list nm_connection_list_filter(struct nm_connection_list *list, 159 | unsigned int count, ...); 160 | 161 | /** 162 | * Measure the length of a list 163 | * @param list: The list to be measures 164 | */ 165 | size_t nm_connection_list_length(struct nm_connection_list *list); 166 | 167 | /** 168 | * Print the whole list onto stdout. 169 | * @param list: List to be printed 170 | */ 171 | void nm_connection_list_dbg_print(struct nm_connection_list *list); 172 | 173 | /** 174 | * Print the whole list onto stderr. 175 | * @param list: List to be printed 176 | */ 177 | void nm_connection_list_dbg_eprint(struct nm_connection_list *list); 178 | 179 | /** 180 | * Print all servers into char buffer. The caller is responsible for releasing the 181 | * buffer with free(). 182 | * @param list: List to be printed 183 | */ 184 | struct string_buffer nm_connection_list_sprint_servers(struct nm_connection_list *list); 185 | 186 | /** 187 | * Return true if the connection is VPN 188 | * @param conn: Single connection to be tested 189 | */ 190 | bool nm_connection_filter_type_vpn(struct nm_connection const *conn); 191 | 192 | /** 193 | * Return true if the connection is default 194 | * @param conn: Single connection to be tested 195 | */ 196 | bool nm_connection_filter_default(struct nm_connection const *conn); 197 | 198 | /** 199 | * Return true if the connection is of type OTHER 200 | * @param conn: Single connection to be tested 201 | */ 202 | bool nm_connection_filter_type_other(struct nm_connection const *conn); 203 | 204 | #endif /* CONNECTION_LIST_H */ 205 | -------------------------------------------------------------------------------- /riggerd/fptr_wlist.c: -------------------------------------------------------------------------------- 1 | /* 2 | * util/fptr_wlist.c - function pointer whitelists. 3 | * 4 | * Copyright (c) 2007, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains functions that check function pointers. 40 | * The functions contain a whitelist of known good callback values. 41 | * Any other values lead to an error. 42 | * 43 | * Due to the listing nature, this file violates all the modularization 44 | * boundaries in the program. 45 | */ 46 | #include "config.h" 47 | #include "fptr_wlist.h" 48 | #include "svr.h" 49 | #include "probe.h" 50 | #include "mini_event.h" 51 | #include "http.h" 52 | #include "update.h" 53 | #ifdef USE_WINSOCK 54 | #include "winrc/netlist.h" 55 | #include "winrc/win_svc.h" 56 | #endif 57 | 58 | int 59 | fptr_whitelist_comm_point(comm_point_callback_t *fptr) 60 | { 61 | if(fptr == &outq_handle_udp) return 1; 62 | else if(fptr == &outq_handle_tcp) return 1; 63 | return 0; 64 | } 65 | 66 | int 67 | fptr_whitelist_comm_point_raw(comm_point_callback_t *fptr) 68 | { 69 | if(fptr == &handle_ssl_accept) return 1; 70 | else if(fptr == &http_get_callback) return 1; 71 | else if(fptr == &control_callback) return 1; 72 | return 0; 73 | } 74 | 75 | int 76 | fptr_whitelist_comm_timer(void (*fptr)(void*)) 77 | { 78 | if(fptr == &outq_timeout) return 1; 79 | else if(fptr == &svr_retry_callback) return 1; 80 | else if(fptr == &http_get_timeout_handler) return 1; 81 | else if(fptr == &selfupdate_timeout) return 1; 82 | else if(fptr == &svr_tcp_callback) return 1; 83 | #ifdef USE_WINSOCK 84 | else if(fptr == &wsvc_cron_cb) return 1; 85 | #endif 86 | return 0; 87 | } 88 | 89 | int 90 | fptr_whitelist_comm_signal(void (*fptr)(int, void*)) 91 | { 92 | (void)fptr; 93 | return 0; 94 | } 95 | 96 | int 97 | fptr_whitelist_event(void (*fptr)(int, short, void *)) 98 | { 99 | if(fptr == &comm_point_udp_callback) return 1; 100 | else if(fptr == &comm_point_udp_ancil_callback) return 1; 101 | else if(fptr == &comm_point_tcp_accept_callback) return 1; 102 | else if(fptr == &comm_point_tcp_handle_callback) return 1; 103 | else if(fptr == &comm_timer_callback) return 1; 104 | else if(fptr == &comm_signal_callback) return 1; 105 | else if(fptr == &comm_point_local_handle_callback) return 1; 106 | else if(fptr == &comm_point_raw_handle_callback) return 1; 107 | #ifdef USE_WINSOCK 108 | else if(fptr == &netlist_change_cb) return 1; 109 | else if(fptr == &worker_win_stop_cb) return 1; 110 | #endif 111 | return 0; 112 | } 113 | 114 | int 115 | fptr_whitelist_rbtree_cmp(int (*fptr) (const void *, const void *)) 116 | { 117 | if(fptr == &mini_ev_cmp) return 1; 118 | return 0; 119 | } 120 | 121 | #ifdef USE_WINSOCK 122 | int fptr_whitelist_enum_reg(void (*fptr) (HKEY, void *)) 123 | { 124 | if(fptr == &enum_reg_set_nameserver) return 1; 125 | return 0; 126 | } 127 | #endif /* USE_WINSOCK */ 128 | 129 | -------------------------------------------------------------------------------- /riggerd/fptr_wlist.h: -------------------------------------------------------------------------------- 1 | /* 2 | * util/fptr_wlist.h - function pointer whitelists. 3 | * 4 | * Copyright (c) 2007, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains functions that check function pointers. 40 | * The functions contain a whitelist of known good callback values. 41 | * Any other values lead to an error. 42 | * 43 | * This prevent heap overflow based exploits, where the callback pointer 44 | * is overwritten by a buffer overflow (apart from this defense, buffer 45 | * overflows should be fixed of course). 46 | * 47 | * Function pointers are used in 48 | * o network code callbacks. 49 | * o rbtree, the assertions are before the critical regions. 50 | * in other places, assertions are before the callback. 51 | */ 52 | 53 | #ifndef UTIL_FPTR_WLIST_H 54 | #define UTIL_FPTR_WLIST_H 55 | #include "netevent.h" 56 | 57 | /** 58 | * Macro to perform an assertion check for fptr wlist checks. 59 | * Does not get disabled in optimize mode. Check adds security by layers. 60 | */ 61 | #define fptr_ok(x) \ 62 | do { if(!(x)) \ 63 | fatal_exit("%s:%d: %s: pointer whitelist %s failed", \ 64 | __FILE__, __LINE__, __func__, #x); \ 65 | } while(0); 66 | 67 | /** 68 | * Check function pointer whitelist for comm_point callback values. 69 | * 70 | * @param fptr: function pointer to check. 71 | * @return false if not in whitelist. 72 | */ 73 | int fptr_whitelist_comm_point(comm_point_callback_t *fptr); 74 | 75 | /** 76 | * Check function pointer whitelist for raw comm_point callback values. 77 | * 78 | * @param fptr: function pointer to check. 79 | * @return false if not in whitelist. 80 | */ 81 | int fptr_whitelist_comm_point_raw(comm_point_callback_t *fptr); 82 | 83 | /** 84 | * Check function pointer whitelist for comm_timer callback values. 85 | * 86 | * @param fptr: function pointer to check. 87 | * @return false if not in whitelist. 88 | */ 89 | int fptr_whitelist_comm_timer(void (*fptr)(void*)); 90 | 91 | /** 92 | * Check function pointer whitelist for comm_signal callback values. 93 | * 94 | * @param fptr: function pointer to check. 95 | * @return false if not in whitelist. 96 | */ 97 | int fptr_whitelist_comm_signal(void (*fptr)(int, void*)); 98 | 99 | /** 100 | * Check function pointer whitelist for event structure callback values. 101 | * This is not called by libevent itself, but checked by netevent. 102 | * 103 | * @param fptr: function pointer to check. 104 | * @return false if not in whitelist. 105 | */ 106 | int fptr_whitelist_event(void (*fptr)(int, short, void *)); 107 | 108 | /** 109 | * Check function pointer whitelist for rbtree cmp callback values. 110 | * 111 | * @param fptr: function pointer to check. 112 | * @return false if not in whitelist. 113 | */ 114 | int fptr_whitelist_rbtree_cmp(int (*fptr) (const void *, const void *)); 115 | 116 | #ifdef USE_WINSOCK 117 | /** whitelist for registry enumeration function */ 118 | int fptr_whitelist_enum_reg(void (*fptr) (HKEY, void *)); 119 | #endif /* USE_WINSOCK */ 120 | 121 | #endif /* UTIL_FPTR_WLIST_H */ 122 | -------------------------------------------------------------------------------- /riggerd/fwd_zones.c: -------------------------------------------------------------------------------- 1 | #include "config.h" 2 | #include 3 | 4 | #include "fwd_zones.h" 5 | #include "../vendor/ccan/json/json.h" 6 | 7 | #ifdef FWD_ZONES_SUPPORT 8 | 9 | struct nm_connection_list yield_connections_from_json(char *json) 10 | { 11 | struct nm_connection_list ret; 12 | nm_connection_list_init(&ret); 13 | 14 | if (json_validate(json) == true) { 15 | //printf("I've got valid json and it looks like this:\n%s\n", json); 16 | JsonNode *node; 17 | JsonNode *connection; 18 | JsonNode *parameter; 19 | 20 | /* Decode the input string and check it again */ 21 | JsonNode *head = json_decode(json); 22 | if (NULL == head || head->tag != JSON_OBJECT) { 23 | json_delete(head); 24 | return ret; 25 | 26 | } 27 | 28 | /* We expect to get a list of connections. Anything else is not valid input, 29 | * even though it might be valid json. */ 30 | node = head->children.head; // now it should be the first dictionary value i.e. connections 31 | if (NULL == node || strncmp(node->key, "connections", 11) != 0) { // and also must be an array 32 | json_delete(head); 33 | return ret; 34 | } 35 | 36 | /* Now we finally have the array of connections and this is 37 | * its head */ 38 | connection = node->children.head; 39 | /* Go through all connections and put them into the connection list ret */ 40 | while (NULL != connection) { 41 | 42 | struct nm_connection *new_conn = (struct nm_connection *)calloc_or_die(sizeof(struct nm_connection)); 43 | nm_connection_init(new_conn); 44 | 45 | /* Read all key:value pairs in each node. Expected values 46 | * are: default, servers, type, zones */ 47 | parameter = connection->children.head; 48 | while (NULL != parameter) { 49 | 50 | // Check JSON key 51 | if (JSON_BOOL == parameter->tag && strncmp(parameter->key, "default", 7) == 0) { 52 | new_conn->default_con = parameter->bool_; 53 | } else if (JSON_STRING == parameter->tag && strncmp(parameter->key, "type", 4) == 0) { 54 | if (strncmp(parameter->string_, "wifi", 4) == 0) { 55 | new_conn->type = NM_CON_WIFI; 56 | } else if (strncmp(parameter->string_, "vpn", 3) == 0) { 57 | new_conn->type = NM_CON_VPN; 58 | } else if (strncmp(parameter->string_, "other", 5) == 0) { 59 | new_conn->type = NM_CON_OTHER; 60 | } else { 61 | new_conn->type = NM_CON_IGNORE; 62 | } 63 | } else if (JSON_ARRAY == parameter->tag && strncmp(parameter->key, "zones", 5) == 0) { 64 | JsonNode *zone = parameter->children.head; 65 | while (NULL != zone) { 66 | string_list_push_back(&new_conn->zones, zone->string_, strlen(zone->string_)); 67 | zone = zone->next; 68 | } 69 | } else if (JSON_ARRAY == parameter->tag && strncmp(parameter->key, "servers", 7) == 0) { 70 | JsonNode *server = parameter->children.head; 71 | while (NULL != server) { 72 | string_list_push_back(&new_conn->servers, server->string_, strlen(server->string_)); 73 | server = server->next; 74 | } 75 | } else { 76 | // TODO: debug output: invalid json key 77 | } 78 | 79 | parameter = parameter->next; 80 | } 81 | 82 | nm_connection_list_push_back(&ret, new_conn); 83 | connection = connection->next; 84 | } 85 | json_delete(head); 86 | } else { 87 | printf("Invalid json input\n"); 88 | // TODO: log error message into syslog 89 | } 90 | 91 | return ret; 92 | 93 | } 94 | 95 | #endif 96 | -------------------------------------------------------------------------------- /riggerd/fwd_zones.h: -------------------------------------------------------------------------------- 1 | #include "connection_list.h" 2 | 3 | #if !defined FWD_ZONES_H && defined FWD_ZONES_SUPPORT 4 | #define FWD_ZONES_H 5 | 6 | // TODO: this should probably go to connection_list.h as well 7 | /** 8 | * Read input in json format and parse it 9 | * into list of connections. In case of failure 10 | * return an empty list. 11 | */ 12 | struct nm_connection_list yield_connections_from_json(char *json); 13 | 14 | #endif /* FWD_ZONES_H */ 15 | -------------------------------------------------------------------------------- /riggerd/lock.c: -------------------------------------------------------------------------------- 1 | #include "config.h" 2 | #include "lock.h" 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | static const char *LF_PATH = __LOCK_FILE_PATH; 10 | static size_t LF_PATH_LEN = sizeof(__LOCK_FILE_PATH); 11 | 12 | static int check_dir = 1; 13 | static int fd = 0; 14 | 15 | void lock_acquire() { 16 | const char* path; 17 | struct flock f = { 18 | .l_type=F_WRLCK, 19 | .l_whence=SEEK_SET, 20 | .l_start=0, 21 | .l_len=0 22 | }; 23 | int ret; 24 | if (check_dir) { 25 | // TODO check & create dir 26 | } 27 | path = LF_PATH; 28 | fd = open(path, O_WRONLY|O_CREAT|O_CLOEXEC, 0600); 29 | if (fd == -1) { 30 | // TODO error handling 31 | return; 32 | } 33 | ret = fcntl(fd, F_SETLKW, f); 34 | if (ret == -1) { 35 | // TODO error handling 36 | return; 37 | } 38 | } 39 | 40 | void lock_release() { 41 | struct flock f = { 42 | .l_type=F_UNLCK, 43 | .l_whence=SEEK_SET, 44 | .l_start=0, 45 | .l_len=0 46 | }; 47 | int ret; 48 | if (fd == 0) { 49 | return; 50 | } 51 | ret = fcntl(fd, F_SETLKW, f); 52 | if (ret == -1) { 53 | // TODO error handling 54 | return; 55 | } 56 | 57 | close(fd); 58 | fd = 0; 59 | } 60 | 61 | void lock_override(const char *path, size_t len) { 62 | LF_PATH = path; 63 | LF_PATH_LEN = len; 64 | check_dir = 0; 65 | } 66 | 67 | -------------------------------------------------------------------------------- /riggerd/lock.h: -------------------------------------------------------------------------------- 1 | /** 2 | * Syncronization primitive to be used by the daemon and script in 3 | * order serialize execution. So far it should be just 1:1 rewrite of 4 | * the Python implementation. 5 | */ 6 | 7 | #if !defined LOCK_H && defined FWD_ZONES_SUPPORT 8 | #define LOCK_H 9 | 10 | #define __LOCK_FILE_DIR "/var/run/dnssec-trigger" 11 | #define __LOCK_FILE_PATH "/var/run/dnssec-trigger/lock" 12 | 13 | /** Check lock file presence and acquire the lock. If the file is 14 | * already locked, block until it is released. 15 | * TODO: possible errors 16 | */ 17 | void lock_acquire(); 18 | 19 | /** 20 | * Release the lock. 21 | * TODO: possible errors 22 | */ 23 | void lock_release(); 24 | 25 | /** 26 | * Override lock file location. For testing purposes only. The function 27 | * stores the pointer, it does not copy the content, so the content must 28 | * live as long as the lock is used. 29 | */ 30 | void lock_override(const char *path, size_t len); 31 | 32 | #endif /* LOCK_H */ 33 | -------------------------------------------------------------------------------- /riggerd/mini_event.h: -------------------------------------------------------------------------------- 1 | /* 2 | * mini-event.h - micro implementation of libevent api, using select() only. 3 | * 4 | * Copyright (c) 2007, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * This file implements part of the event(3) libevent api. 39 | * The back end is only select. Max number of fds is limited. 40 | * Max number of signals is limited, one handler per signal only. 41 | * And one handler per fd. 42 | * 43 | * Although limited to select() and a max (1024) open fds, it 44 | * is efficient: 45 | * o dispatch call caches fd_sets to use. 46 | * o handler calling takes time ~ to the number of fds. 47 | * o timeouts are stored in a redblack tree, sorted, so take log(n). 48 | * Timeouts are only accurate to the second (no subsecond accuracy). 49 | * To avoid cpu hogging, fractional timeouts are rounded up to a whole second. 50 | */ 51 | 52 | #ifndef MINI_EVENT_H 53 | #define MINI_EVENT_H 54 | 55 | #if defined(USE_MINI_EVENT) && !defined(USE_WINSOCK) 56 | 57 | #ifndef HAVE_EVENT_BASE_FREE 58 | #define HAVE_EVENT_BASE_FREE 59 | #endif 60 | 61 | /** event timeout */ 62 | #define EV_TIMEOUT 0x01 63 | /** event fd readable */ 64 | #define EV_READ 0x02 65 | /** event fd writable */ 66 | #define EV_WRITE 0x04 67 | /** event signal */ 68 | #define EV_SIGNAL 0x08 69 | /** event must persist */ 70 | #define EV_PERSIST 0x10 71 | 72 | /* needs our redblack tree */ 73 | #include "rbtree.h" 74 | 75 | /** max number of file descriptors to support */ 76 | #define MAX_FDS 1024 77 | /** max number of signals to support */ 78 | #define MAX_SIG 32 79 | 80 | /** event base */ 81 | struct event_base 82 | { 83 | /** sorted by timeout (absolute), ptr */ 84 | rbtree_t* times; 85 | /** array of 0 - maxfd of ptr to event for it */ 86 | struct event** fds; 87 | /** max fd in use */ 88 | int maxfd; 89 | /** capacity - size of the fds array */ 90 | int capfd; 91 | /* fdset for read write, for fds ready, and added */ 92 | fd_set 93 | /** fds for reading */ 94 | reads, 95 | /** fds for writing */ 96 | writes, 97 | /** fds determined ready for use */ 98 | ready, 99 | /** ready plus newly added events. */ 100 | content; 101 | /** array of 0 - maxsig of ptr to event for it */ 102 | struct event** signals; 103 | /** if we need to exit */ 104 | int need_to_exit; 105 | /** where to store time in seconds */ 106 | uint32_t* time_secs; 107 | /** where to store time in microseconds */ 108 | struct timeval* time_tv; 109 | }; 110 | 111 | /** 112 | * Event structure. Has some of the event elements. 113 | */ 114 | struct event { 115 | /** node in timeout rbtree */ 116 | rbnode_t node; 117 | /** is event already added */ 118 | int added; 119 | 120 | /** event base it belongs to */ 121 | struct event_base *ev_base; 122 | /** fd to poll or -1 for timeouts. signal number for sigs. */ 123 | int ev_fd; 124 | /** what events this event is interested in, see EV_.. above. */ 125 | short ev_events; 126 | /** timeout value */ 127 | struct timeval ev_timeout; 128 | 129 | /** callback to call: fd, eventbits, userarg */ 130 | void (*ev_callback)(int, short, void *arg); 131 | /** callback user arg */ 132 | void *ev_arg; 133 | }; 134 | 135 | /* function prototypes (some are as they appear in event.h) */ 136 | /** create event base */ 137 | void *event_init(uint32_t* time_secs, struct timeval* time_tv); 138 | /** get version */ 139 | const char *event_get_version(void); 140 | /** get polling method, select */ 141 | const char *event_get_method(void); 142 | /** run select in a loop */ 143 | int event_base_dispatch(struct event_base *); 144 | /** exit that loop */ 145 | int event_base_loopexit(struct event_base *, struct timeval *); 146 | /** free event base. Free events yourself */ 147 | void event_base_free(struct event_base *); 148 | /** set content of event */ 149 | void event_set(struct event *, int, short, void (*)(int, short, void *), void *); 150 | /** add event to a base. You *must* call this for every event. */ 151 | int event_base_set(struct event_base *, struct event *); 152 | /** add event to make it active. You may not change it with event_set anymore */ 153 | int event_add(struct event *, struct timeval *); 154 | /** remove event. You may change it again */ 155 | int event_del(struct event *); 156 | 157 | /** add a timer */ 158 | #define evtimer_add(ev, tv) event_add(ev, tv) 159 | /** remove a timer */ 160 | #define evtimer_del(ev) event_del(ev) 161 | 162 | /* uses different implementation. Cannot mix fd/timeouts and signals inside 163 | * the same struct event. create several event structs for that. */ 164 | /** install signal handler */ 165 | int signal_add(struct event *, struct timeval *); 166 | /** set signal event contents */ 167 | #define signal_set(ev, x, cb, arg) \ 168 | event_set(ev, x, EV_SIGNAL|EV_PERSIST, cb, arg) 169 | /** remove signal handler */ 170 | int signal_del(struct event *); 171 | 172 | #endif /* USE_MINI_EVENT and not USE_WINSOCK */ 173 | 174 | /** compare events in tree, based on timevalue, ptr for uniqueness */ 175 | int mini_ev_cmp(const void* a, const void* b); 176 | 177 | #endif /* MINI_EVENT_H */ 178 | -------------------------------------------------------------------------------- /riggerd/probe.h: -------------------------------------------------------------------------------- 1 | /* 2 | * probe.h - dnssec-trigger DNSSEC probes 3 | * 4 | * Copyright (c) 2011, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains the probe definition. 40 | */ 41 | 42 | #ifndef PROBE_H 43 | #define PROBE_H 44 | struct comm_point; 45 | struct comm_reply; 46 | struct http_get; 47 | struct http_fetch; 48 | struct outq; 49 | struct svr; 50 | 51 | /** 52 | * probe structure that contains the probe details for one IP address. 53 | */ 54 | struct probe_ip { 55 | struct probe_ip* next; 56 | /* the IP address probed */ 57 | char* name; 58 | /* to authority? */ 59 | int to_auth; 60 | /* for dnstcp? */ 61 | int dnstcp; 62 | /* for ssl? */ 63 | struct ssllist* ssldns; 64 | /* is this a http probe */ 65 | int to_http; 66 | /* is http on ipv6 (or v4)? */ 67 | int http_ip6; 68 | /* destination port */ 69 | int port; 70 | 71 | /* the ssl context (if any) for this destination address */ 72 | void* sslctx; 73 | 74 | /* DS query, or NULL if done */ 75 | struct outq* ds_c; 76 | /* DNSKEY query, or NULL if done */ 77 | struct outq* dnskey_c; 78 | /* nodata query probes NSEC3, or NULL if done or not used */ 79 | struct outq* nsec3_c; 80 | 81 | /* A,AAAA query to resolve http hostname, or NULL if done or not used*/ 82 | struct outq* host_c; 83 | /* http query in progress */ 84 | struct http_get* http; 85 | /* desc of http (available even when done and http is NULL) */ 86 | char* http_desc; 87 | 88 | /* if probe has finished */ 89 | int finished; 90 | /* result for this IP, true if DNSSEC OK */ 91 | int works; 92 | /* string with explanation of failure */ 93 | char* reason; 94 | /* if a packet has been received by a query (i.e. network is up) */ 95 | int got_packet; 96 | }; 97 | 98 | /** outstanding query */ 99 | struct outq { 100 | struct sockaddr_storage addr; 101 | socklen_t addrlen; 102 | uint16_t qid; 103 | uint16_t qtype; 104 | int recurse; /* if true: recursive probe */ 105 | const char* qname; /* reference to a static string */ 106 | int timeout; /* in msec */ 107 | int on_tcp; /* if we are using TCP */ 108 | int on_ssl; /* if we are using SSL */ 109 | int port; /* port number (mostly 53) */ 110 | int edns; /* if edns yes */ 111 | int cdflag; /* if CD flag on query */ 112 | struct comm_point* c; 113 | struct comm_timer* timer; 114 | struct probe_ip* probe; /* reference only to owner */ 115 | }; 116 | 117 | #define QUERY_START_TIMEOUT 100 /* msec */ 118 | #define QUERY_END_TIMEOUT 1000 /* msec */ 119 | #define QUERY_TCP_TIMEOUT 3000 /* msec */ 120 | 121 | /** start the probe process for a new set of IPs. 122 | * in a string, with whitespace in between 123 | * the string may be altered. */ 124 | void probe_start(char* ips); 125 | 126 | /** delete and stop probe */ 127 | void probe_delete(struct probe_ip* p); 128 | 129 | /** probe list delete */ 130 | void probe_list_delete(struct probe_ip* list); 131 | 132 | /** handle probe results */ 133 | int outq_handle_udp(struct comm_point* c, void* my_arg, int error, 134 | struct comm_reply *reply_info); 135 | int outq_handle_tcp(struct comm_point* c, void* my_arg, int error, 136 | struct comm_reply *reply_info); 137 | 138 | /** outstanding query UDP timeout handler */ 139 | void outq_timeout(void* arg); 140 | 141 | void probe_cache_done(void); 142 | void probe_all_done(void); 143 | void probe_unsafe_test(void); 144 | void probe_tcp_test(void); 145 | void probe_http_test(void); 146 | void probe_ssl_test(void); 147 | void probe_setup_cache(struct svr* svr, struct probe_ip* p); 148 | void probe_setup_hotspot_signon(struct svr* svr); 149 | void probe_setup_dnstcp(struct svr* svr); 150 | 151 | /** true if probe is a cache IP, a DNS server from the DHCP hook */ 152 | int probe_is_cache(struct probe_ip* p); 153 | 154 | /** Create new outgoing query: 155 | * @param ip: server to send to (IP4 or IP6 string). 156 | * @param tp: rr type 157 | * @param domain: domain name in text format. 158 | * @param recurse: +RD flag or not. 159 | * @param p: parent pointer. 160 | * @param tcp: false for UDP, true for TCP 161 | * @param onssl: if true, (and TCP) uses SSL wrap. 162 | * @param port: port number for query 163 | * @param edns: if true, DO flag set. 164 | * @param cdflag: if true, CD flag set. 165 | * @return new outq or out of memory. 166 | */ 167 | struct outq* outq_create(const char* ip, int tp, const char* domain, 168 | int recurse, struct probe_ip* p, int tcp, int onssl, int port, 169 | int edns, int cdflag); 170 | 171 | /* delete and stop outq */ 172 | void outq_delete(struct outq* outq); 173 | 174 | #endif /* PROBE_H */ 175 | -------------------------------------------------------------------------------- /riggerd/reshook.h: -------------------------------------------------------------------------------- 1 | /* 2 | * reshook.h - dnssec-trigger resolv.conf hooks for adjusting name resolution 3 | * 4 | * Copyright (c) 2011, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains the unbound hooks for adjusting the name resolution 40 | * on the system (to 127.0.0.1). 41 | */ 42 | 43 | #ifndef RESHOOKS_H 44 | #define RESHOOKS_H 45 | struct cfg; 46 | struct probe_ip; 47 | 48 | /** 49 | * Set the system to resolve at 127.0.0.1 (where unbound is running) 50 | * @param cfg: with config options. 51 | */ 52 | void hook_resolv_localhost(struct cfg* cfg); 53 | 54 | /** 55 | * Set the system to resolve at the list of 'cache' (recursive) probes in 56 | * the given list. The original servers are used, not DNSTCP recursive probes. 57 | * @param cfg: with config options. 58 | */ 59 | void hook_resolv_iplist(struct cfg* cfg, struct probe_ip* list); 60 | 61 | /** 62 | * Flush the DNS caches on the system, if somehow possible 63 | * @param cfg: with config options. 64 | */ 65 | void hook_resolv_flush(struct cfg* cfg); 66 | 67 | #ifdef HOOKS_OSX 68 | /** on OSX we need to restore resolv.conf after user login */ 69 | void restore_resolv_osx(struct cfg* cfg); 70 | #endif /* HOOKS_OSX */ 71 | 72 | /** 73 | * Unregister the override we put in place. 74 | * The override survives reboots, this uninit is for uninstall. 75 | */ 76 | void hook_resolv_uninstall(struct cfg* cfg); 77 | 78 | #endif /* RESHOOKS_H */ 79 | -------------------------------------------------------------------------------- /riggerd/store.c: -------------------------------------------------------------------------------- 1 | #include "config.h" 2 | #include 3 | #include 4 | 5 | #include "store.h" 6 | #include "string_list.h" 7 | #include "log.h" 8 | 9 | struct store store_init(const char *dir, const char *full_path, const char *full_path_tmp) { 10 | struct string_list cache; 11 | struct store s; 12 | FILE *fp; 13 | size_t line_len = 512; 14 | ssize_t read_len; 15 | char* line; 16 | string_list_init(&cache); 17 | s.dir = dir, 18 | s.path = full_path, 19 | s.path_tmp = full_path_tmp, 20 | s.cache = cache; 21 | // Read cache into the string list 22 | fp = fopen(full_path, "r"); 23 | if (fp == NULL) { 24 | log_err("cannot open %s: %s", full_path, strerror(errno)); 25 | return s; 26 | } 27 | line = (char *)calloc_or_die(line_len); 28 | memset(line, 0, line_len); 29 | while ((read_len = getline(&line, &line_len, fp)) != -1){ 30 | if(read_len > 0 && line[read_len-1]=='\n') 31 | line[--read_len] = 0; /* remove \n */ 32 | string_list_push_back(&s.cache, line, read_len); 33 | memset(line, 0, line_len); 34 | } 35 | if(ferror(fp)) { 36 | log_err("error reading %s: %s", full_path, strerror(errno)); 37 | } 38 | free(line); 39 | fclose(fp); 40 | return s; 41 | } 42 | 43 | int store_commit(const struct store *self) { 44 | struct string_entry* iter; 45 | // Open the tmp file 46 | FILE *fp = fopen(self->path_tmp, "w"); 47 | if (fp == NULL) { 48 | log_err("cannot open %s for write: %s", self->path_tmp, strerror(errno)); 49 | return -1; 50 | } 51 | // Write its content 52 | FOR_EACH_STRING_IN_LIST(iter, &self->cache) { 53 | fprintf(fp, "%s\n", iter->string); 54 | } 55 | // Close it 56 | fclose(fp); 57 | return rename(self->path_tmp, self->path); 58 | } 59 | 60 | void store_destroy(struct store *self) { 61 | string_list_clear(&self->cache); 62 | } 63 | 64 | void store_remove(struct store *self, char *string, size_t len) { 65 | string_list_remove(&self->cache, string, len); 66 | } 67 | 68 | void store_add(struct store *self, char *string, size_t len) { 69 | if (!string_list_contains(&self->cache, string, len)) { 70 | string_list_push_back(&self->cache, string, len); 71 | } 72 | } 73 | 74 | int store_contains(struct store *self, char *string, size_t len) { 75 | return string_list_contains(&self->cache, string, len); 76 | } 77 | -------------------------------------------------------------------------------- /riggerd/store.h: -------------------------------------------------------------------------------- 1 | /** 2 | * Persistent storage in /var/run/dnssec-trigger/ directory. 3 | */ 4 | 5 | #if !defined STORE_H && defined FWD_ZONES_SUPPORT 6 | #define STORE_H 7 | 8 | #include "string_list.h" 9 | 10 | /* Directory used for storage of all files available through 11 | * this module. */ 12 | #define STORE_BASE_DIR "/var/run/dnssec-trigger" 13 | /* Concatenate file name with the base directory. */ 14 | #define STORE_PATH(NAME) (STORE_BASE_DIR "/" NAME) 15 | /* Concatenate file name with the base directory and append ".tmp" 16 | * to the path. As the name suggests this file will be stored 17 | * temporarily and eventually it will replace the normal file. */ 18 | #define STORE_PATH_TMP(NAME) (STORE_BASE_DIR "/" NAME ".tmp") 19 | 20 | struct store { 21 | const char *dir; 22 | const char *path; 23 | const char *path_tmp; 24 | struct string_list cache; 25 | }; 26 | 27 | /** 28 | * Create the store structure from directory name and absolute path of the file used for 29 | * persistent storage. The last argument is an absolute path of the file with tmp suffix. 30 | */ 31 | struct store store_init(const char *dir, const char *full_path, const char *full_path_tmp); 32 | 33 | /** 34 | * Write the cache back to disk into file specified in the 'path' member 35 | */ 36 | int store_commit(const struct store *self); 37 | 38 | /** 39 | * Destroy cache 40 | */ 41 | void store_destroy(struct store *self); 42 | 43 | /* 44 | * Remove a string from the cache 45 | */ 46 | void store_remove(struct store *self, char *string, size_t len); 47 | 48 | /* 49 | * Push a string into the cache 50 | */ 51 | void store_add(struct store *self, char *string, size_t len); 52 | 53 | 54 | /* 55 | * Return true if the cache contains the string 56 | */ 57 | int store_contains(struct store *self, char *string, size_t len); 58 | 59 | /** 60 | * Macro that wraps up the init function in order to reduce typing. 61 | */ 62 | #define STORE_INIT(NAME) store_init((STORE_BASE_DIR),(STORE_PATH(NAME)),(STORE_PATH_TMP(NAME))) 63 | 64 | #endif /* STORE_H */ 65 | -------------------------------------------------------------------------------- /riggerd/string_buffer.h: -------------------------------------------------------------------------------- 1 | #include "config.h" 2 | 3 | #if !defined STRING_BUFFER_H && defined FWD_ZONES_SUPPORT 4 | #define STRING_BUFFER_H 5 | 6 | #include 7 | 8 | /** 9 | * Just a fat pointer wrapping char pointer 10 | */ 11 | struct string_buffer { 12 | /** String itself */ 13 | char* string; 14 | /** Length of the string buffer */ 15 | size_t length; 16 | }; 17 | 18 | #define string_builder(STR) \ 19 | { \ 20 | .string = (STR), \ 21 | .length = sizeof((STR)), \ 22 | } 23 | 24 | #endif /* STRING_BUFFER_H */ 25 | 26 | -------------------------------------------------------------------------------- /riggerd/string_list.h: -------------------------------------------------------------------------------- 1 | #include "config.h" 2 | 3 | #if !defined STRING_LIST_H && defined FWD_ZONES_SUPPORT 4 | #define STRING_LIST_H 5 | 6 | #include 7 | #include 8 | 9 | #define FOR_EACH_STRING_IN_LIST(ITER, LIST) for ((ITER) = (LIST)->first; (ITER) != NULL; (ITER) = (ITER)->next) 10 | 11 | /** 12 | * Linked list of strings 13 | */ 14 | struct string_list { 15 | /** A linked list of strings */ 16 | struct string_entry *first; 17 | }; 18 | 19 | /** 20 | * One node in the string list 21 | */ 22 | struct string_entry { 23 | /** Next in list */ 24 | struct string_entry* next; 25 | /** String owned by this list 26 | * Do not use this pointer elsewhere 27 | */ 28 | char* string; 29 | /** Length of the string buffer */ 30 | size_t length; 31 | /** Heap allocated extension of this entry. It can be of any type and if not NULL 32 | * it will be freed during the cleanup. 33 | */ 34 | void* extension; 35 | }; 36 | 37 | // TODO: move somewhere else 38 | /* 39 | * Thin wrapper around malloc. It either gets a valid memory 40 | * or exit the whole process. 41 | */ 42 | void* calloc_or_die(size_t size); 43 | 44 | /** 45 | * Initialize a new list of strings 46 | * @param list: New list 47 | */ 48 | void string_list_init(struct string_list* list); 49 | 50 | /** 51 | * Clear the list and free all contained buffers 52 | * @param list: List to be cleared. To free the structure itself is caller responsibility. 53 | */ 54 | void string_list_clear(struct string_list* list); 55 | 56 | /** 57 | * Push new string at the end of the list. The string 58 | * is copied into the node. 59 | * @param list: List to append to 60 | * @param new_value: String to be appended 61 | * @param buffer_size: Size of the buffer from which the string is copied 62 | */ 63 | void string_list_push_back(struct string_list* list, const char* new_value, const size_t buffer_size); 64 | 65 | /** 66 | * Find out whether the list contains the given value 67 | * @param list: List to check 68 | * @param new_value: String to be found 69 | * @param buffer_size: Size of the string buffer 70 | */ 71 | int string_list_contains(const struct string_list* list, const char* value, const size_t buffer_size); 72 | 73 | /** 74 | * Duplicate the list 75 | * @param original: List to copy 76 | * @param copy: New list 77 | */ 78 | void string_list_duplicate(const struct string_list* original, struct string_list *copy); 79 | 80 | /** 81 | * Copy the second list and append it to the first one 82 | * @param original: The list that gets extended 83 | * @param append: The list that is copied 84 | */ 85 | void string_list_copy_and_append(struct string_list* original, struct string_list *append); 86 | 87 | /** 88 | * Find out whether the list contains the given value and remove it 89 | * @param list: List to check 90 | * @param new_value: String to be removed 91 | * @param buffer_size: Size of the string buffer 92 | */ 93 | void string_list_remove(struct string_list* list, const char* value, const size_t buffer_size); 94 | 95 | /** 96 | * Find out the size of given list 97 | * @param list: List to check 98 | */ 99 | size_t string_list_length(const struct string_list* list); 100 | 101 | /** 102 | * Compare content of two lists. Every value must be unique. 103 | * @param l1: First list 104 | * @param l2: Second list 105 | */ 106 | int string_list_is_equal(const struct string_list* l1, const struct string_list* l2); 107 | 108 | /** 109 | * Print list of strings onto one line without newline at the end. 110 | * @param list: List to be printed 111 | */ 112 | void string_list_dbg_print(const struct string_list* list); 113 | void string_list_dbg_eprint(const struct string_list* list); 114 | void string_list_dbg_print_inner(const struct string_list* list, FILE *fp); 115 | 116 | /** 117 | * Print list into a buffer. Be careful, you have to free the buffer 118 | * yourself. 119 | * @param list: List to print 120 | * @param buffer: Buffer to print the list into 121 | * @param len: size of the buffer 122 | * @return: success >= 0, -1 = list does not fit into the buffer 123 | */ 124 | int string_list_sprint(const struct string_list* list, char *buffer, size_t len); 125 | 126 | #endif /* STRING_LIST_H */ 127 | 128 | -------------------------------------------------------------------------------- /riggerd/ubhook.h: -------------------------------------------------------------------------------- 1 | /* 2 | * ubhook.h - dnssec-trigger unbound control hooks for adjusting that server 3 | * 4 | * Copyright (c) 2011, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains the unbound hooks for adjusting the unbound validating 40 | * DNSSEC resolver. 41 | */ 42 | 43 | #ifdef FWD_ZONES_SUPPORT 44 | 45 | #include "connection_list.h" 46 | 47 | #endif 48 | 49 | #ifndef UBHOOKS_H 50 | #define UBHOOKS_H 51 | struct cfg; 52 | struct probe_ip; 53 | 54 | /** 55 | * Set the unbound server to go to the authorities 56 | * @param cfg: the config options. 57 | */ 58 | void hook_unbound_auth(struct cfg* cfg); 59 | 60 | /** 61 | * Set the unbound server to go to the given cache 62 | * @param cfg: the config options. 63 | */ 64 | void hook_unbound_cache(struct cfg* cfg, const char* ip); 65 | 66 | /** 67 | * Set the unbound server to go to the working probed servers. 68 | * @param cfg: the config options. 69 | * @param list: the working servers in this list are used. 70 | */ 71 | void hook_unbound_cache_list(struct cfg* cfg, struct probe_ip* list); 72 | 73 | /** 74 | * Set the unbound server to go dark. It gets no connections. 75 | * In reality, it sets unbound to forward to 127.0.0.127 and thus no upstream. 76 | * Unbound by default does not send queries to 127/8. 77 | * @param cfg: the config options. 78 | */ 79 | void hook_unbound_dark(struct cfg* cfg); 80 | 81 | /* IP address that makes unbound go dark, no upstream. unbound has 82 | * donotquery 127.0.0.0/8 by default */ 83 | #define UNBOUND_DARK_IP "127.0.0.127" 84 | 85 | /** 86 | * Detect if unbound supports the tcp-upstream option (since 1.4.13). 87 | * @param cfg: the config options. 88 | */ 89 | int hook_unbound_supports_tcp_upstream(struct cfg* cfg); 90 | 91 | /** 92 | * Detect if unbound supports the ssl-upstream option (since 1.4.14). 93 | * @param cfg: the config options. 94 | */ 95 | int hook_unbound_supports_ssl_upstream(struct cfg* cfg); 96 | 97 | /** 98 | * Set unbound to use tcp upstream. 99 | * @param cfg: the config options. 100 | * @param tcp80_ip4: if true, use those IP addresses. 101 | * @param tcp80_ip6: if true, use those IP addresses. 102 | * @param tcp443_ip4: if true, use those IP addresses. 103 | * @param tcp443_ip6: if true, use those IP addresses. 104 | */ 105 | void hook_unbound_tcp_upstream(struct cfg* cfg, int tcp80_ip4, int tcp80_ip6, 106 | int tcp443_ip4, int tcp443_ip6); 107 | 108 | /** 109 | * Set unbound to use ssl upstream. 110 | * @param cfg: the config options. 111 | * @param ssl443_ip4: if true, use those IP addresses. 112 | * @param ssl443_ip6: if true, use those IP addresses. 113 | */ 114 | void hook_unbound_ssl_upstream(struct cfg* cfg, int ssl443_ip4, int ssl443_ip6); 115 | 116 | #ifdef FWD_ZONES_SUPPORT 117 | 118 | /** 119 | * Run unbound list_forwards and parse output into the return structure 120 | */ 121 | struct nm_connection_list hook_unbound_list_forwards(struct cfg* cfg); 122 | 123 | /** 124 | * For testing purposes only. 125 | */ 126 | struct nm_connection_list hook_unbound_list_forwards_inner(struct cfg* cfg, FILE *fp); 127 | 128 | /** 129 | * Run unbound list_local_zones and parse output into the return structure 130 | */ 131 | struct string_list hook_unbound_list_local_zones(struct cfg* cfg); 132 | 133 | /** 134 | * For testing purposes only. 135 | */ 136 | struct string_list hook_unbound_list_local_zones_inner(struct cfg* cfg, FILE *fp); 137 | 138 | /** 139 | * 140 | */ 141 | int hook_unbound_add_forward_zone_from_connection(struct nm_connection *con); 142 | int hook_unbound_add_forward_zone(struct string_buffer zone, struct string_buffer servers); 143 | int hook_unbound_add_forward_zone_inner(struct string_buffer exe, struct string_buffer zone, struct string_buffer servers); 144 | 145 | /** 146 | * 147 | */ 148 | int hook_unbound_remove_forward_zone(struct string_buffer zone); 149 | int hook_unbound_remove_forward_zone_inner(struct string_buffer exe, struct string_buffer zone); 150 | 151 | 152 | /** 153 | * Call unbound-control local_zone 154 | */ 155 | int hook_unbound_add_local_zone(struct string_buffer zone, struct string_buffer type); 156 | int hook_unbound_add_local_zone_inner(struct string_buffer exe, struct string_buffer zone, struct string_buffer type); 157 | 158 | 159 | /** 160 | * Call unbound-control local_zone_remove 161 | */ 162 | int hook_unbound_remove_local_zone(struct string_buffer zone); 163 | int hook_unbound_remove_local_zone_inner(struct string_buffer exe, struct string_buffer zone); 164 | 165 | 166 | #endif 167 | 168 | #endif /* UBHOOKS_H */ 169 | -------------------------------------------------------------------------------- /riggerd/update.h: -------------------------------------------------------------------------------- 1 | /* 2 | * update.h - dnssec-trigger update 3 | * 4 | * Copyright (c) 2012, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains the functions to run update check and download the update 40 | */ 41 | 42 | #ifndef UPDATE_H 43 | #define UPDATE_H 44 | #include 45 | struct outq; 46 | struct http_get; 47 | struct svr; 48 | struct cfg; 49 | struct comm_timer; 50 | 51 | /** 52 | * The update data 53 | */ 54 | struct selfupdate { 55 | /** the server */ 56 | struct svr* svr; 57 | /** the config to use (reference) */ 58 | struct cfg* cfg; 59 | 60 | /** when was the last time the update was performed, if 0 never. 61 | * At this time the version check TXT returned successfully. */ 62 | time_t last_check; 63 | /** we have to update (and ask the user) */ 64 | int update_available; 65 | /** did the user reply to the question */ 66 | int user_replied; 67 | /** did the user agree to install the update */ 68 | int user_okay; 69 | /** if this flag is on update with the unstable test version 70 | * This is used to test the software update mechanism. 71 | * Or to distribute test software to some participants. 72 | */ 73 | int test_flag; 74 | 75 | /** query for TXT record with version and hash */ 76 | struct outq* txt_query; 77 | /** the probed version (or NULL if not probed) as string */ 78 | char* version_available; 79 | /** the hash of this installer version (or NULL if not probed) */ 80 | uint8_t* hash; 81 | /** length of hash */ 82 | size_t hashlen; 83 | 84 | /** get address for http fetch, or NULL on its failure */ 85 | struct outq* addr_4; 86 | struct outq* addr_6; 87 | /** the address list for downloads */ 88 | ldns_rr_list* addr_list_4; 89 | ldns_rr_list* addr_list_6; 90 | /** http get operation that fetches the installer (or NULL if not) */ 91 | struct http_get* download_http4; 92 | struct http_get* download_http6; 93 | /** filename with downloaded file (or NULL) */ 94 | char* download_file; 95 | /** filename of the download url (no directory part) */ 96 | char* filename; 97 | /** if we have downloaded to file and hash is okay 98 | * we have to delete this file so it does not clog up the system */ 99 | int file_available; 100 | 101 | /** timer that sets selfupdate_desired after 24h in svr */ 102 | struct comm_timer* timer; 103 | }; 104 | 105 | /** retry time (in seconds) between version checks */ 106 | #define SELFUPDATE_RETRY (2*3600) 107 | /** 24h time (in seconds) between version checks */ 108 | #define SELFUPDATE_NEXT_CHECK (24*3600) 109 | /** 110 | * The dnssec trigger domain name (where the TXT records are) 111 | * TXT records at {win,src,osx}.{test,version}.ourdomain 112 | * with TXT "version" "sha256" 113 | */ 114 | #define DNSSECTRIGGER_DOMAIN "dnssec-trigger.nlnetlabs.nl" 115 | /** the download site for new software updates. */ 116 | #define DNSSECTRIGGER_DOWNLOAD_HOST "www.nlnetlabs.nl" 117 | /** the download URL for the software updates, the directory (start with /) */ 118 | #define DNSSECTRIGGER_DOWNLOAD_URLPRE "/downloads/dnssec-trigger/" 119 | 120 | /** create new selfupdate structure (empty). */ 121 | struct selfupdate* selfupdate_create(struct svr* svr, struct cfg* cfg); 122 | /** delete selfupdate structure */ 123 | void selfupdate_delete(struct selfupdate* se); 124 | 125 | /** start selfupdate 126 | * We must be in a DNSSEC secure state. unbound at 127.0.0.1 must then 127 | * be pointed at this DNSSEC secureness and its AD flag is trusted. 128 | */ 129 | void selfupdate_start(struct selfupdate* se); 130 | 131 | /** the user indicates his support for the update (or nonsupport) */ 132 | void selfupdate_userokay(struct selfupdate* se, int okay); 133 | 134 | /** the outq query is done, error reason (or NULL if works) */ 135 | void selfupdate_outq_done(struct selfupdate* se, struct outq* outq, 136 | ldns_pkt* pkt, const char* reason); 137 | 138 | /** see if version x is newer than y */ 139 | int version_is_newer(const char* x, const char* y); 140 | 141 | /** timeout handler for selfupdate timer */ 142 | void selfupdate_timeout(void* arg); 143 | 144 | /** routine called when http has connected to the server (but no data yet) */ 145 | void selfupdate_http_connected(struct selfupdate* se, struct http_get* hg); 146 | 147 | /** routine called when http is done */ 148 | void selfupdate_http_get_done(struct selfupdate* se, struct http_get* hg, 149 | char* reason); 150 | 151 | #endif /* UPDATE_H */ 152 | -------------------------------------------------------------------------------- /test/clang-analysis.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | # clang analysis test script 3 | 4 | if test ! -x "`which clang 2>&1`"; then 5 | echo "No clang in path" 6 | exit 0 7 | fi 8 | 9 | PRE="." 10 | # test if assertions are enabled 11 | if grep "^#define DO_DEBUG" $PRE/config.h >/dev/null; then 12 | : 13 | else 14 | echo "DO_DEBUG (--enable-debug) is not enabled, skip test" 15 | # no debug means no assertions, and clang analyzer uses 16 | # the assertions to make inferences. 17 | exit 0 18 | fi 19 | 20 | # read value from Makefile 21 | # $1: result variable name 22 | # $2: string on Makefile 23 | # $3: Makefile location 24 | read_value () { 25 | x=`grep "$2" $3 | sed -e "s/$2//"` 26 | eval $1="'""$x""'" 27 | # print what we just read 28 | #echo $1"="'"'"`eval echo '$'$1`"'"' 29 | } 30 | 31 | # read some values from the Makefile 32 | read_value srcdir '^srcdir=' $PRE/Makefile 33 | read_value gui '^gui=' $PRE/Makefile 34 | read_value CPPFLAGS '^CPPFLAGS=' $PRE/Makefile 35 | read_value LIBOBJS '^LIBOBJS= *' $PRE/Makefile 36 | read_value GTK_CFLAGS '^GTK_CFLAGS= *' $PRE/Makefile 37 | 38 | # turn libobjs into C files 39 | compatfiles=`echo "$LIBOBJS" | sed -e 's?..LIBOBJDIR.?compat/?g' -e 's/.U.o/.c/g'` 40 | 41 | odir=`pwd` 42 | cd $srcdir 43 | # check the files in the srcdir 44 | fail="no" 45 | for x in riggerd/*.c panel/attach.c $compatfiles test/*.c; do 46 | echo clang --analyze $CPPFLAGS $x 47 | plist=`basename $x .c`.plist 48 | rm -rf $plist 49 | (cd "$odir"; clang --analyze $CPPFLAGS $srcdir/$x 2>&1 ) | tee tmp.$$ 50 | if grep -e warning -e error tmp.$$ >/dev/null; then 51 | fail="yes" 52 | fails="$fails $x" 53 | fi 54 | rm -rf $plist tmp.$$ 55 | done 56 | 57 | if test "$gui" = "gtk"; then 58 | x="panel/panel.c" 59 | echo clang --analyze $CPPFLAGS $GTK_CFLAGS $x 60 | plist=`basename $x .c`.plist 61 | rm -rf $plist 62 | (cd "$odir"; clang --analyze $CPPFLAGS $GTK_CFLAGS $srcdir/$x 2>&1 ) | tee tmp.$$ 63 | if grep -e warning -e error tmp.$$ >/dev/null; then 64 | fail="yes" 65 | fails="$fails $x" 66 | fi 67 | rm -rf $plist tmp.$$ 68 | fi 69 | 70 | echo 71 | if test "$fail" = "yes"; then 72 | echo "Failures" 73 | echo "create reports in file.plist dir with clang --analyze --analyzer-output html $CPPFLAGS""$fails" 74 | exit 1 75 | fi 76 | echo "OK" 77 | exit 0 78 | -------------------------------------------------------------------------------- /test/json.c: -------------------------------------------------------------------------------- 1 | #include "../config.h" 2 | #include 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | #include "../riggerd/fwd_zones.h" 11 | #include "../riggerd/connection_list.h" 12 | #include "../riggerd/string_list.h" 13 | #include "../riggerd/string_buffer.h" 14 | #include "../vendor/ccan/json/json.h" 15 | 16 | char *json = 17 | "{" 18 | "\n \"connections\": [" 19 | "\n {" 20 | "\n \"default\": false," 21 | "\n \"servers\": [" 22 | "\n \"10.2.0.4\"," 23 | "\n \"10.9.2.4\"," 24 | "\n \"10.2.0.6\"" 25 | "\n ]," 26 | "\n \"type\": \"wifi\"," 27 | "\n \"zones\": [" 28 | "\n \"example.com\"" 29 | "\n ]" 30 | "\n }," 31 | "\n {" 32 | "\n \"default\": true," 33 | "\n \"servers\": [" 34 | "\n \"10.60.0.16\"," 35 | "\n \"10.67.5.56\"" 36 | "\n ]," 37 | "\n \"type\": \"other\"," 38 | "\n \"zones\": [" 39 | "\n \"brno.example.com\"," 40 | "\n \"prague.example.com\"," 41 | "\n \"finance.prague.example.com\"," 42 | "\n \"laboratory.prague.example.com\"," 43 | "\n \"lab2.prague.example.com\"" 44 | "\n ]" 45 | "\n }," 46 | "\n {" 47 | "\n \"default\": false," 48 | "\n \"servers\": [" 49 | "\n \"10.148.8.37\"," 50 | "\n \"10.145.245.24\"" 51 | "\n ]," 52 | "\n \"type\": \"vpn\"," 53 | "\n \"zones\": [" 54 | "\n \"example.com\"" 55 | "\n ]" 56 | "\n }" 57 | "\n ]" 58 | "\n}\n"; 59 | 60 | #define assert_true(x) assert_true_fp((x), __FILE__, __LINE__) 61 | static void assert_true_fp(int x, const char* f, int l) 62 | { 63 | assert(x); 64 | if(!x) { 65 | printf("%s:%d: assert_true failed\n", f, l); 66 | exit(1); 67 | } 68 | } 69 | 70 | /* A test case that does nothing and succeeds. */ 71 | static void null_test_success(void) { 72 | } 73 | 74 | static void load_json_into_list_and_test_length(void) { 75 | struct nm_connection_list l = yield_connections_from_json(json); 76 | assert_true(nm_connection_list_length(&l) == 3); 77 | nm_connection_list_clear(&l); 78 | } 79 | 80 | static void filter_connection_list_and_test_length0(void) { 81 | struct nm_connection_list l = yield_connections_from_json(json); 82 | struct nm_connection_list l2 = nm_connection_list_filter(&l, 0); 83 | assert_true(nm_connection_list_length(&l2) == 3); 84 | nm_connection_list_clear(&l2); 85 | nm_connection_list_clear(&l); 86 | } 87 | 88 | static void filter_connection_list_and_test_length1(void) { 89 | struct nm_connection_list l = yield_connections_from_json(json); 90 | struct nm_connection_list l2 = nm_connection_list_filter(&l, 1, &nm_connection_filter_type_vpn); 91 | assert_true(nm_connection_list_length(&l2) == 1); 92 | nm_connection_list_clear(&l2); 93 | nm_connection_list_clear(&l); 94 | } 95 | 96 | int main() { 97 | // printf("Test json parser:\n%s\n", json); 98 | // struct nm_connection_list l = yield_connections_from_json(json); 99 | // nm_connection_list_dbg_print(&l); 100 | // printf("Length is: %zu\n", nm_connection_list_length(&l)); 101 | // struct nm_connection_list l2 = nm_connection_list_filter(&l, 0); 102 | // printf("Length is: %zu\n", nm_connection_list_length(&l2)); 103 | // struct nm_connection_list l3 = nm_connection_list_filter(&l, 1, &nm_connection_filter_type_vpn); 104 | // printf("Length is: %zu\n", nm_connection_list_length(&l3)); 105 | // struct nm_connection_list l4 = nm_connection_list_filter(&l, 1, &nm_connection_filter_default); 106 | // printf("Length is: %zu\n", nm_connection_list_length(&l4)); 107 | // struct nm_connection_list l5 = nm_connection_list_filter(&l, 2, &nm_connection_filter_type_other, &nm_connection_filter_default); 108 | // printf("Length is: %zu\n", nm_connection_list_length(&l5)); 109 | // struct nm_connection_list l6 = nm_connection_list_filter(&l, 2, &nm_connection_filter_type_vpn, &nm_connection_filter_default); 110 | // printf("Length is: %zu\n", nm_connection_list_length(&l6)); 111 | 112 | // { 113 | // struct string_buffer buffer = nm_connection_list_sprint_servers(&l); 114 | // printf("Servers: %s\n", buffer.string); 115 | // free(buffer.string); 116 | // } 117 | 118 | // char *buffer = calloc_or_die(1000); 119 | // string_list_sprint(&l.first->self->servers, buffer, 1000); 120 | // printf("%s\n", buffer); 121 | // free(buffer); 122 | // nm_connection_list_clear(&l); 123 | 124 | /* run tests */ 125 | printf("null_test_success: "); 126 | null_test_success(); 127 | printf("OK\n"); 128 | 129 | printf("load_json_into_list_and_test_length: "); 130 | load_json_into_list_and_test_length(); 131 | printf("OK\n"); 132 | 133 | printf("filter_connection_list_and_test_length0: "); 134 | filter_connection_list_and_test_length0(); 135 | printf("OK\n"); 136 | 137 | printf("filter_connection_list_and_test_length1: "); 138 | filter_connection_list_and_test_length1(); 139 | printf("OK\n"); 140 | 141 | printf("\n"); 142 | printf("OK\n"); 143 | return 0; 144 | } 145 | -------------------------------------------------------------------------------- /test/list_forwards_example: -------------------------------------------------------------------------------- 1 | . IN forward 10.12.15.16 2 | ny.mylovelycorporate.io. IN forward +i 192.168.1.1 10.12.15.16 3 | c.f.ip6.arpa. IN forward +i 192.168.1.1 10.12.15.16 4 | d.f.ip6.arpa. IN forward +i 192.168.1.1 10.12.15.16 5 | 10.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 6 | 16.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 7 | 17.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 8 | 18.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 9 | 19.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 10 | 20.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 11 | 21.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 12 | 22.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 13 | 23.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 14 | 24.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 15 | 25.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 16 | 26.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 17 | 27.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 18 | 28.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 19 | 29.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 20 | 30.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 21 | 31.172.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 22 | 168.192.in-addr.arpa. IN forward +i 192.168.1.1 10.12.15.16 23 | -------------------------------------------------------------------------------- /test/list_local_zones_example: -------------------------------------------------------------------------------- 1 | 255.255.255.255.in-addr.arpa. static 2 | test. static 3 | invalid. static 4 | -------------------------------------------------------------------------------- /test/servers-list-ipv4: -------------------------------------------------------------------------------- 1 | 1.2.3.4 2 | 192.168.168.168 3 | -------------------------------------------------------------------------------- /test/tmp/commit-cache: -------------------------------------------------------------------------------- 1 | 5.6.7.8 2 | 9.10.11.12 3 | -------------------------------------------------------------------------------- /test/unbound-control-fake.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | if [ $# -eq 3 ] 4 | then 5 | if [ $1 = "local_zone" ] && [ $2 = "test" ] && [ $3 = "static" ] 6 | then 7 | echo ok 8 | else 9 | echo fail 10 | fi 11 | elif [ $# -eq 2 ] 12 | then 13 | if [ $1 = "local_zone_remove" ] && [ $2 = "test" ] 14 | then 15 | echo ok 16 | else 17 | echo fail 18 | fi 19 | else 20 | echo fail 21 | fi 22 | 23 | -------------------------------------------------------------------------------- /vendor/ccan/json/BSD-MIT: -------------------------------------------------------------------------------- 1 | Permission is hereby granted, free of charge, to any person obtaining a copy 2 | of this software and associated documentation files (the "Software"), to deal 3 | in the Software without restriction, including without limitation the rights 4 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 5 | copies of the Software, and to permit persons to whom the Software is 6 | furnished to do so, subject to the following conditions: 7 | 8 | The above copyright notice and this permission notice shall be included in 9 | all copies or substantial portions of the Software. 10 | 11 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 12 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 13 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 14 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 15 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 16 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 17 | THE SOFTWARE. 18 | -------------------------------------------------------------------------------- /vendor/ccan/json/_info: -------------------------------------------------------------------------------- 1 | #include "config.h" 2 | #include 3 | #include 4 | 5 | /** 6 | * json - Parse and generate JSON (JavaScript Object Notation) 7 | * 8 | * This is a library for encoding and decoding JSON that strives to be 9 | * easy to learn, use, and incorporate into an application. 10 | * 11 | * JSON (JavaScript Object Notation) facilitates passing data among different 12 | * programming languages, particularly JavaScript. It looks like this: 13 | * 14 | * [ 15 | * { 16 | * "id": 1, 17 | * "firstname": "John", 18 | * "lastname": "Smith", 19 | * "email": "john@example.com", 20 | * "likes_pizza": false 21 | * }, 22 | * { 23 | * "id": 2, 24 | * "firstname": "Linda", 25 | * "lastname": "Jones", 26 | * "email": null, 27 | * "likes_pizza": true 28 | * } 29 | * ] 30 | * 31 | * Example: 32 | * #include 33 | * #include 34 | * #include 35 | * #include 36 | * 37 | * static int find_number(JsonNode *object, const char *name, double *out) 38 | * { 39 | * JsonNode *node = json_find_member(object, name); 40 | * if (node && node->tag == JSON_NUMBER) { 41 | * *out = node->number_; 42 | * return 1; 43 | * } 44 | * return 0; 45 | * } 46 | * 47 | * static void solve_pythagorean(JsonNode *triple) 48 | * { 49 | * double a = 0, b = 0, c = 0; 50 | * int a_given, b_given, c_given; 51 | * 52 | * if (triple->tag != JSON_OBJECT) { 53 | * fprintf(stderr, "Error: Expected a JSON object.\n"); 54 | * exit(EXIT_FAILURE); 55 | * } 56 | * 57 | * a_given = find_number(triple, "a", &a); 58 | * b_given = find_number(triple, "b", &b); 59 | * c_given = find_number(triple, "c", &c); 60 | * 61 | * if (a_given + b_given + c_given != 2) { 62 | * fprintf(stderr, "Error: I need two sides to compute the length of the third.\n"); 63 | * exit(EXIT_FAILURE); 64 | * } 65 | * 66 | * if (a_given && b_given) { 67 | * c = sqrt(a*a + b*b); 68 | * json_append_member(triple, "c", json_mknumber(c)); 69 | * } else if (a_given && c_given) { 70 | * b = sqrt(c*c - a*a); 71 | * json_append_member(triple, "b", json_mknumber(b)); 72 | * } else if (b_given && c_given) { 73 | * a = sqrt(c*c - b*b); 74 | * json_append_member(triple, "a", json_mknumber(a)); 75 | * } 76 | * } 77 | * 78 | * int main(void) 79 | * { 80 | * JsonNode *triples = json_mkarray(); 81 | * 82 | * json_append_element(triples, json_decode("{\"a\": 3, \"b\": 4}")); 83 | * json_append_element(triples, json_decode("{\"a\": 5, \"c\": 13}")); 84 | * json_append_element(triples, json_decode("{\"b\": 24, \"c\": 25}")); 85 | * 86 | * JsonNode *triple; 87 | * json_foreach(triple, triples) 88 | * solve_pythagorean(triple); 89 | * 90 | * char *tmp = json_stringify(triples, "\t"); 91 | * puts(tmp); 92 | * free(tmp); 93 | * 94 | * json_delete(triples); 95 | * return 0; 96 | * } 97 | * 98 | * Author: Joey Adams 99 | * Version: 0.1 100 | * License: MIT 101 | */ 102 | int main(int argc, char *argv[]) 103 | { 104 | /* Expect exactly one argument */ 105 | if (argc != 2) 106 | return 1; 107 | 108 | if (strcmp(argv[1], "depends") == 0) { 109 | /* Nothing */ 110 | return 0; 111 | } 112 | 113 | if (strcmp(argv[1], "libs") == 0) { 114 | printf("m\n"); /* Needed for sqrt() used in example code above. */ 115 | return 0; 116 | } 117 | 118 | return 1; 119 | } 120 | -------------------------------------------------------------------------------- /vendor/ccan/json/json.h: -------------------------------------------------------------------------------- 1 | /* 2 | Copyright (C) 2011 Joseph A. Adams (joeyadams3.14159@gmail.com) 3 | All rights reserved. 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in 13 | all copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21 | THE SOFTWARE. 22 | */ 23 | 24 | #ifndef CCAN_JSON_H 25 | #define CCAN_JSON_H 26 | 27 | #include 28 | #include 29 | 30 | typedef enum { 31 | JSON_NULL, 32 | JSON_BOOL, 33 | JSON_STRING, 34 | JSON_NUMBER, 35 | JSON_ARRAY, 36 | JSON_OBJECT, 37 | } JsonTag; 38 | 39 | typedef struct JsonNode JsonNode; 40 | 41 | struct JsonNode 42 | { 43 | /* only if parent is an object or array (NULL otherwise) */ 44 | JsonNode *parent; 45 | JsonNode *prev, *next; 46 | 47 | /* only if parent is an object (NULL otherwise) */ 48 | char *key; /* Must be valid UTF-8. */ 49 | 50 | JsonTag tag; 51 | union { 52 | /* JSON_BOOL */ 53 | bool bool_; 54 | 55 | /* JSON_STRING */ 56 | char *string_; /* Must be valid UTF-8. */ 57 | 58 | /* JSON_NUMBER */ 59 | double number_; 60 | 61 | /* JSON_ARRAY */ 62 | /* JSON_OBJECT */ 63 | struct { 64 | JsonNode *head, *tail; 65 | } children; 66 | }; 67 | }; 68 | 69 | /*** Encoding, decoding, and validation ***/ 70 | 71 | JsonNode *json_decode (const char *json); 72 | char *json_encode (const JsonNode *node); 73 | char *json_encode_string (const char *str); 74 | char *json_stringify (const JsonNode *node, const char *space); 75 | void json_delete (JsonNode *node); 76 | 77 | bool json_validate (const char *json); 78 | 79 | /*** Lookup and traversal ***/ 80 | 81 | JsonNode *json_find_element (JsonNode *array, int index); 82 | JsonNode *json_find_member (JsonNode *object, const char *key); 83 | 84 | JsonNode *json_first_child (const JsonNode *node); 85 | 86 | #define json_foreach(i, object_or_array) \ 87 | for ((i) = json_first_child(object_or_array); \ 88 | (i) != NULL; \ 89 | (i) = (i)->next) 90 | 91 | /*** Construction and manipulation ***/ 92 | 93 | JsonNode *json_mknull(void); 94 | JsonNode *json_mkbool(bool b); 95 | JsonNode *json_mkstring(const char *s); 96 | JsonNode *json_mknumber(double n); 97 | JsonNode *json_mkarray(void); 98 | JsonNode *json_mkobject(void); 99 | 100 | void json_append_element(JsonNode *array, JsonNode *element); 101 | void json_prepend_element(JsonNode *array, JsonNode *element); 102 | void json_append_member(JsonNode *object, const char *key, JsonNode *value); 103 | void json_prepend_member(JsonNode *object, const char *key, JsonNode *value); 104 | 105 | void json_remove_from_parent(JsonNode *node); 106 | 107 | /*** Debugging ***/ 108 | 109 | /* 110 | * Look for structure and encoding problems in a JsonNode or its descendents. 111 | * 112 | * If a problem is detected, return false, writing a description of the problem 113 | * to errmsg (unless errmsg is NULL). 114 | */ 115 | bool json_check(const JsonNode *node, char errmsg[256]); 116 | 117 | #endif 118 | -------------------------------------------------------------------------------- /vendor/ccan/json/test/common.h: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include 5 | #include 6 | 7 | static char *chomp(char *s) 8 | { 9 | char *e; 10 | 11 | if (s == NULL || *s == 0) 12 | return s; 13 | 14 | e = strchr(s, 0); 15 | if (e[-1] == '\n') 16 | *--e = 0; 17 | return s; 18 | } 19 | -------------------------------------------------------------------------------- /vendor/ccan/json/test/run-construction.c: -------------------------------------------------------------------------------- 1 | /* Build a list of numbers with various appends and prepends, verify them by testing against their encoded value, do pointer consistency checks each time, do element lookups, and remove items as well. */ 2 | 3 | #include "common.h" 4 | 5 | #define should_be(var, expected) should_be_(var, #var, expected) 6 | 7 | static void should_be_(const JsonNode *node, const char *name, const char *expected) 8 | { 9 | char errmsg[256]; 10 | char *encoded; 11 | 12 | if (!json_check(node, errmsg)) { 13 | fail("Invariants check failed: %s", errmsg); 14 | return; 15 | } 16 | 17 | encoded = json_encode(node); 18 | 19 | if (strcmp(encoded, expected) == 0) 20 | pass("%s is %s", name, expected); 21 | else 22 | fail("%s should be %s, but is actually %s", name, expected, encoded); 23 | 24 | free(encoded); 25 | } 26 | 27 | static void test_string(void) 28 | { 29 | JsonNode *str; 30 | 31 | str = json_mkstring("Hello\tworld!\n\001"); 32 | should_be(str, "\"Hello\\tworld!\\n\\u0001\""); 33 | json_delete(str); 34 | 35 | str = json_mkstring("\"\\\b\f\n\r\t"); 36 | should_be(str, "\"\\\"\\\\\\b\\f\\n\\r\\t\""); 37 | json_delete(str); 38 | } 39 | 40 | static void test_number(void) 41 | { 42 | JsonNode *num; 43 | 44 | num = json_mknumber(5678901234.0); 45 | should_be(num, "5678901234"); 46 | json_delete(num); 47 | 48 | num = json_mknumber(-5678901234.0); 49 | should_be(num, "-5678901234"); 50 | json_delete(num); 51 | 52 | num = json_mknumber(0.0 / 0.0); 53 | should_be(num, "null"); 54 | json_delete(num); 55 | } 56 | 57 | static void test_array(void) 58 | { 59 | JsonNode *array; 60 | JsonNode *children[5 + 1]; 61 | 62 | array = json_mkarray(); 63 | should_be(array, "[]"); 64 | 65 | children[1] = json_mknumber(1); 66 | children[2] = json_mknumber(2); 67 | children[3] = json_mknumber(3); 68 | children[4] = json_mknumber(4); 69 | children[5] = json_mknumber(5); 70 | 71 | json_append_element(array, children[3]); 72 | should_be(array, "[3]"); 73 | 74 | json_remove_from_parent(children[3]); 75 | should_be(array, "[]"); 76 | 77 | json_prepend_element(array, children[3]); 78 | should_be(array, "[3]"); 79 | 80 | json_prepend_element(array, children[2]); 81 | should_be(array, "[2,3]"); 82 | 83 | json_append_element(array, children[4]); 84 | should_be(array, "[2,3,4]"); 85 | 86 | json_delete(children[3]); 87 | should_be(array, "[2,4]"); 88 | 89 | json_prepend_element(array, children[1]); 90 | should_be(array, "[1,2,4]"); 91 | 92 | json_delete(children[1]); 93 | should_be(array, "[2,4]"); 94 | 95 | json_delete(children[4]); 96 | should_be(array, "[2]"); 97 | 98 | ok1(json_find_element(array, 0) == children[2]); 99 | ok1(json_find_element(array, -1) == NULL); 100 | ok1(json_find_element(array, 1) == NULL); 101 | 102 | json_append_element(array, children[5]); 103 | should_be(array, "[2,5]"); 104 | 105 | ok1(json_find_element(array, 0) == children[2]); 106 | ok1(json_find_element(array, 1) == children[5]); 107 | ok1(json_find_element(array, -1) == NULL); 108 | ok1(json_find_element(array, 2) == NULL); 109 | 110 | json_delete(children[2]); 111 | json_delete(children[5]); 112 | should_be(array, "[]"); 113 | 114 | ok1(json_find_element(array, -1) == NULL); 115 | ok1(json_find_element(array, 0) == NULL); 116 | ok1(json_find_element(array, 1) == NULL); 117 | 118 | json_delete(array); 119 | } 120 | 121 | static void test_object(void) 122 | { 123 | JsonNode *object; 124 | JsonNode *children[5 + 1]; 125 | 126 | object = json_mkobject(); 127 | should_be(object, "{}"); 128 | 129 | children[1] = json_mknumber(1); 130 | children[2] = json_mknumber(2); 131 | children[3] = json_mknumber(3); 132 | 133 | ok1(json_find_member(object, "one") == NULL); 134 | ok1(json_find_member(object, "two") == NULL); 135 | ok1(json_find_member(object, "three") == NULL); 136 | 137 | json_append_member(object, "one", children[1]); 138 | should_be(object, "{\"one\":1}"); 139 | 140 | ok1(json_find_member(object, "one") == children[1]); 141 | ok1(json_find_member(object, "two") == NULL); 142 | ok1(json_find_member(object, "three") == NULL); 143 | 144 | json_prepend_member(object, "two", children[2]); 145 | should_be(object, "{\"two\":2,\"one\":1}"); 146 | 147 | ok1(json_find_member(object, "one") == children[1]); 148 | ok1(json_find_member(object, "two") == children[2]); 149 | ok1(json_find_member(object, "three") == NULL); 150 | 151 | json_append_member(object, "three", children[3]); 152 | should_be(object, "{\"two\":2,\"one\":1,\"three\":3}"); 153 | 154 | ok1(json_find_member(object, "one") == children[1]); 155 | ok1(json_find_member(object, "two") == children[2]); 156 | ok1(json_find_member(object, "three") == children[3]); 157 | 158 | json_delete(object); 159 | } 160 | 161 | int main(void) 162 | { 163 | JsonNode *node; 164 | 165 | (void) chomp; 166 | 167 | plan_tests(49); 168 | 169 | ok1(json_find_element(NULL, 0) == NULL); 170 | ok1(json_find_member(NULL, "") == NULL); 171 | ok1(json_first_child(NULL) == NULL); 172 | 173 | node = json_mknull(); 174 | should_be(node, "null"); 175 | json_delete(node); 176 | 177 | node = json_mkbool(false); 178 | should_be(node, "false"); 179 | json_delete(node); 180 | 181 | node = json_mkbool(true); 182 | should_be(node, "true"); 183 | json_delete(node); 184 | 185 | test_string(); 186 | test_number(); 187 | test_array(); 188 | test_object(); 189 | 190 | return exit_status(); 191 | } 192 | -------------------------------------------------------------------------------- /vendor/ccan/json/test/run-decode-encode.c: -------------------------------------------------------------------------------- 1 | #include "common.h" 2 | 3 | int main(void) 4 | { 5 | const char *strings_file = "test/test-strings"; 6 | const char *strings_reencoded_file = "test/test-strings-reencoded"; 7 | FILE *f, *f2; 8 | char buffer[1024], buffer2[1024]; 9 | 10 | plan_tests(90); 11 | 12 | f = fopen(strings_file, "rb"); 13 | if (f == NULL) { 14 | diag("Could not open %s: %s", strings_file, strerror(errno)); 15 | return 1; 16 | } 17 | f2 = fopen(strings_reencoded_file, "rb"); 18 | if (f2 == NULL) { 19 | diag("Could not open %s: %s", strings_reencoded_file, strerror(errno)); 20 | return 1; 21 | } 22 | 23 | while (fgets(buffer, sizeof(buffer), f)) { 24 | const char *s = chomp(buffer); 25 | bool valid; 26 | JsonNode *node; 27 | 28 | if (expect_literal(&s, "valid ")) { 29 | valid = true; 30 | } else if (expect_literal(&s, "invalid ")) { 31 | valid = false; 32 | } else { 33 | fail("Invalid line in test-strings: %s", buffer); 34 | continue; 35 | } 36 | 37 | node = json_decode(s); 38 | 39 | if (valid) { 40 | char *reencoded; 41 | char errmsg[256]; 42 | 43 | if (node == NULL) { 44 | fail("%s is valid, but json_decode returned NULL", s); 45 | continue; 46 | } 47 | 48 | if (!json_check(node, errmsg)) { 49 | fail("Corrupt tree produced by json_decode: %s", errmsg); 50 | continue; 51 | } 52 | 53 | reencoded = json_encode(node); 54 | 55 | if (!fgets(buffer2, sizeof(buffer2), f2)) { 56 | fail("test-strings-reencoded is missing this line: %s", reencoded); 57 | continue; 58 | } 59 | chomp(buffer2); 60 | 61 | ok(strcmp(reencoded, buffer2) == 0, "re-encode %s -> %s", s, reencoded); 62 | 63 | free(reencoded); 64 | json_delete(node); 65 | } else if (node != NULL) { 66 | fail("%s is invalid, but json_decode returned non-NULL", s); 67 | continue; 68 | } 69 | } 70 | 71 | if (ferror(f) || fclose(f) != 0 || ferror(f2) || fclose(f2) != 0) { 72 | diag("I/O error reading test data."); 73 | return 1; 74 | } 75 | 76 | return exit_status(); 77 | } 78 | -------------------------------------------------------------------------------- /vendor/ccan/json/test/run-stringify.c: -------------------------------------------------------------------------------- 1 | #include "common.h" 2 | 3 | static char buf1[256], buf2[256]; 4 | 5 | /* Used for pass and fail messages */ 6 | static char *quote_string(const char *str, char buf[256]) 7 | { 8 | char *out = buf; 9 | 10 | *out++ = '"'; 11 | for (; *str != 0; str++) { 12 | if (out - buf > 256 - 5) { 13 | /* String is too long. End it with `...' */ 14 | out = buf + 256 - 5; 15 | *out++ = '.'; 16 | *out++ = '.'; 17 | *out++ = '.'; 18 | break; 19 | } 20 | switch (*str) { 21 | case '\t': 22 | *out++ = '\\'; 23 | *out++ = 't'; 24 | break; 25 | case '\n': 26 | *out++ = '\\'; 27 | *out++ = 'n'; 28 | break; 29 | case '"': 30 | *out++ = '\\'; 31 | *out++ = '"'; 32 | break; 33 | case '\\': 34 | *out++ = '\\'; 35 | *out++ = '\\'; 36 | break; 37 | default: 38 | *out++ = *str; 39 | break; 40 | } 41 | } 42 | *out++ = '"'; 43 | 44 | *out = 0; 45 | return buf; 46 | } 47 | 48 | static void test_stringify(const char *input, const char *expected) 49 | { 50 | JsonNode *node = NULL; 51 | char *enc = NULL; 52 | char *strn = NULL; 53 | char *str = NULL; 54 | 55 | node = json_decode(input); 56 | if (node == NULL) { 57 | fail("Failed to decode %s", input); 58 | goto end; 59 | } 60 | 61 | enc = json_encode(node); 62 | if (strcmp(enc, input) != 0) { 63 | fail("%s re-encodes to %s. Either encode/decode is broken, or the input string needs to be normalized", input, enc); 64 | goto end; 65 | } 66 | 67 | strn = json_stringify(node, NULL); 68 | if (strcmp(strn, enc) != 0) { 69 | fail("json_stringify with NULL space produced a different string than json_encode"); 70 | goto end; 71 | } 72 | 73 | str = json_stringify(node, "\t"); 74 | if (strcmp(str, expected) != 0) { 75 | fail("Expected %s, but json_stringify produced %s", 76 | quote_string(expected, buf1), quote_string(str, buf2)); 77 | goto end; 78 | } 79 | 80 | pass("stringify %s", input); 81 | 82 | end: 83 | json_delete(node); 84 | free(enc); 85 | free(strn); 86 | free(str); 87 | } 88 | 89 | int main(void) 90 | { 91 | (void) chomp; 92 | 93 | plan_tests(9); 94 | 95 | test_stringify("[]", "[]"); 96 | test_stringify("[1]", "[\n\t1\n]"); 97 | test_stringify("[1,2,3]", "[\n\t1,\n\t2,\n\t3\n]"); 98 | test_stringify("[[]]", "[\n\t[]\n]"); 99 | test_stringify("[[1,2],[3,4]]", "[\n\t[\n\t\t1,\n\t\t2\n\t],\n\t[\n\t\t3,\n\t\t4\n\t]\n]"); 100 | 101 | test_stringify("{}", "{}"); 102 | test_stringify("{\"one\":1}", "{\n\t\"one\": 1\n}"); 103 | test_stringify("{\"one\":1,\"t*\":[2,3,10]}", "{\n\t\"one\": 1,\n\t\"t*\": [\n\t\t2,\n\t\t3,\n\t\t10\n\t]\n}"); 104 | test_stringify("{\"a\":{\"1\":1,\"2\":2},\"b\":{\"3\":[null,false,true,\"\\f\"]}}", 105 | "{\n\t\"a\": {\n\t\t\"1\": 1,\n\t\t\"2\": 2\n\t},\n\t\"b\": {\n\t\t\"3\": [\n\t\t\tnull,\n\t\t\tfalse,\n\t\t\ttrue,\n\t\t\t\"\\f\"\n\t\t]\n\t}\n}"); 106 | 107 | return exit_status(); 108 | } 109 | -------------------------------------------------------------------------------- /vendor/ccan/json/test/run-validate.c: -------------------------------------------------------------------------------- 1 | #include "common.h" 2 | 3 | int main(void) 4 | { 5 | const char *strings_file = "test/test-strings"; 6 | FILE *f; 7 | char buffer[1024]; 8 | 9 | plan_tests(224); 10 | 11 | f = fopen(strings_file, "rb"); 12 | if (f == NULL) { 13 | diag("Could not open %s: %s", strings_file, strerror(errno)); 14 | return 1; 15 | } 16 | 17 | while (fgets(buffer, sizeof(buffer), f)) { 18 | const char *s = chomp(buffer); 19 | bool valid; 20 | 21 | if (expect_literal(&s, "valid ")) { 22 | valid = true; 23 | } else if (expect_literal(&s, "invalid ")) { 24 | valid = false; 25 | } else { 26 | fail("Invalid line in test-strings: %s", buffer); 27 | continue; 28 | } 29 | 30 | if (strcmp(s, "\"1\\u2\"") == 0) 31 | puts("here"); 32 | 33 | if (json_validate(s) == valid) { 34 | pass("%s %s", valid ? "valid" : "invalid", s); 35 | } else { 36 | fail("%s is %s, but json_validate returned %s", 37 | s, 38 | valid ? "valid" : "invalid", 39 | valid ? "false" : "true"); 40 | } 41 | } 42 | 43 | if (ferror(f) || fclose(f) != 0) { 44 | diag("I/O error reading test strings."); 45 | return 1; 46 | } 47 | 48 | return exit_status(); 49 | } 50 | -------------------------------------------------------------------------------- /vendor/ccan/json/test/test-strings: -------------------------------------------------------------------------------- 1 | invalid 2 | invalid 3 | invalid " 4 | invalid [,] 5 | invalid [) 6 | invalid []] 7 | invalid [} 8 | invalid {,} 9 | invalid {] 10 | invalid ["1":2] 11 | invalid [1,2,] 12 | invalid [1:2} 13 | invalid {"1":2,} 14 | invalid {1:2} 15 | invalid {"1":2, "2.5" : [3, 4, {}, {"5": ["6"], [7 ]}]} 16 | invalid {"1":2, "2.5" : [3, 4, {}, {"5": ["6"], [7]}]} 17 | invalid {"1":2, "2.5" : [3, 4, {}, {"5": ["6"], "7" :[8 ]}] 18 | invalid {"1":2, "2.5" : [3, 4, {}, {"5": ["6"], "7" :[8 ]}]] 19 | invalid {"1":2, "3":4 20 | invalid "1\u2" 21 | invalid [,2] 22 | invalid "3 23 | invalid "3" "4" 24 | invalid [3[4] 25 | invalid [3[4]] 26 | invalid [3, [4, [5], 6] 7, 8 9] 27 | invalid [3, [4, [5], 6] 7, 8, 9] 28 | invalid [3, [4, [5], 6], 7, 8 9] 29 | invalid {"hello":true, "bye":false, null} 30 | invalid {"hello":true, "bye":false, null:null} 31 | invalid "hi 32 | invalid "hi""" 33 | invalid {"hi": "bye"] 34 | invalid "\uD800\uD800" 35 | invalid "\uD800\uDBFF" 36 | invalid "\UD834\UDD1E" 37 | invalid "\uDB00" 38 | invalid "\uDB00\uDBFF" 39 | valid "\uFFFE" 40 | valid "\uFFFF" 41 | invalid . 42 | valid "" 43 | valid [] 44 | valid {} 45 | invalid +. 46 | valid 0.5 47 | invalid 0.e1 48 | valid {"1":{}} 49 | valid {"1":2} 50 | valid {"1":2, "2.5" : [3, 4, {}, {"5": ["6"]}]} 51 | valid {"1":2, "2.5" : [3, 4, {}, {"5": ["6"], "7" :[8 ]}]} 52 | valid 1234 53 | valid -1234 54 | valid {"1":2, "3":4} 55 | invalid +1234 56 | invalid ++1234 57 | valid 123.456e142 58 | valid 123.456e-142 59 | valid 123.456e+142 60 | invalid 123.e-142 61 | valid "1\u2000" 62 | valid "1\u20001" 63 | valid 2 64 | invalid .246e-142 65 | invalid .2e-142 66 | valid 3 67 | invalid .3 68 | valid "3" 69 | valid [3] 70 | invalid +3. 71 | valid 3.2e+1 72 | valid [3, [4]] 73 | valid [3, [4, [5]]] 74 | valid [3, [4, [5], 6]] 75 | valid [3, [4, [5], 6], 7] 76 | valid [3, [4, [5], 6], 7, 8] 77 | valid [3, [4, [5], 6], 7, 8, 9] 78 | invalid +3.5 79 | invalid .3e 80 | invalid .3e1 81 | invalid .3e-1 82 | invalid .3e+1 83 | invalid 3.e1 84 | invalid 3.e+1 85 | valid 3e+1 86 | invalid .5 87 | invalid +.5 88 | invalid .5e+1 89 | valid [ 7] 90 | valid [7 ] 91 | valid [7] 92 | invalid .e-14234 93 | valid "hello" 94 | valid ["hello"] 95 | valid ["hello", "bye"] 96 | valid ["hello", "bye\n"] 97 | valid ["hello", "bye\n\r\t"] 98 | valid ["hello", "bye\n\r\t\b"] 99 | valid ["hello", "bye\n\r\t\b",true] 100 | valid ["hello", "bye\n\r\t\b",true , false] 101 | valid ["hello", "bye\n\r\t\b",true , false, null] 102 | invalid ["hello", "bye\n\r\t\v"] 103 | valid {"hello":true} 104 | valid {"hello":true, "bye":false} 105 | valid {"hello":true, "bye":false, "foo":["one","two","three"]} 106 | valid "hi" 107 | valid ["hi"] 108 | valid ["hi", "bye"] 109 | valid {"hi": "bye"} 110 | valid ["hi", "bye", 3] 111 | valid ["hi", "bye[", 3] 112 | valid "\u0007" 113 | valid "\u0008" 114 | valid "\u0009" 115 | valid "\u0010" 116 | valid "\u0020" 117 | valid "\u10000" 118 | valid "\u1234" 119 | valid "\u99999" 120 | valid "\ud800\udc00" 121 | valid "\uD800\uDC00" 122 | valid "\uD834\uDD1E" 123 | valid "\uDBFF\uDFFF" 124 | valid "\uFFFD" 125 | valid "\uFFFF" 126 | invalid hello 127 | valid [32, 1] 128 | invalid [32, 129 | valid "\uD800\uDC00" 130 | valid "\n" 131 | valid "hello" 132 | valid "hello\u0009world" 133 | valid "hello" 134 | valid "hello\n" 135 | valid "hello" 136 | valid 3 137 | invalid 3. 138 | invalid .3 139 | valid 0.3 140 | invalid 0.3e 141 | invalid 0.3e+ 142 | valid 0.3e+5 143 | valid 0.3e-5 144 | valid 0.3e5 145 | valid "hello" 146 | invalid +3 147 | valid -3 148 | invalid -3. 149 | valid -3.1 150 | invalid .5 151 | invalid 5. 152 | invalid 5.e1 153 | valid 0.5 154 | invalid .3e1 155 | invalid .3e+1 156 | invalid .3e-1 157 | invalid .3e-1 .5 158 | invalid .3e-1.5 159 | invalid .3e+1.5 160 | invalid .3e+. 161 | invalid .3e+.5 162 | invalid .3e+1.5 163 | invalid 9.3e+1.5 164 | invalid 9.e+1.5 165 | invalid 9.e+ 166 | invalid 9.e+1 167 | valid "\"" 168 | valid "\"3.5" 169 | valid "\"." 170 | invalid "\".". 171 | valid "\"....." 172 | invalid "\"\"\"\""" 173 | invalid ["\"\"\"\"", .5] 174 | invalid [.5] 175 | valid ["\"\"\"\"", 0.5] 176 | invalid ["\"\"\"\"", .5] 177 | invalid ["\"\"\"\"",.5] 178 | invalid ["\"",.5] 179 | invalid ["\".5",.5] 180 | invalid ["\".5",".5\"".5] 181 | invalid ["\".5",".5\"", .5] 182 | invalid ["\".5",".5\"",.5] 183 | valid ["\".5",".5\"",0.5] 184 | invalid {"key":/*comment*/"value"} 185 | invalid {"key":/*comment"value"} 186 | invalid {"key":"value"}/* 187 | invalid {"key":"value"}/**/ 188 | invalid {"key":"value"}/***/ 189 | invalid {"key":"value"}/**// 190 | invalid {"key":"value"}/**/// 191 | invalid {"key":"value"}/**///---- 192 | invalid {"key":"value"}# 193 | invalid {"key":"value"}#{ 194 | invalid {"key":"value"}#{} 195 | invalid {"key":"value"}#, 196 | invalid {"key":"value"/**/, "k2":"v2"} 197 | valid "\u0027" 198 | invalid "hello\'" 199 | invalid 'hello\'' 200 | invalid 'hello' 201 | invalid 'hell\'o' 202 | invalid '\'hello' 203 | invalid '\'hello\'' 204 | invalid \'hello\' 205 | invalid 'hello\' 206 | invalid ['hello\'] 207 | invalid ['hello\''] 208 | invalid ['hello"'] 209 | invalid ['hello\"'] 210 | invalid ['hello"o'] 211 | invalid ['"'] 212 | invalid '"' 213 | invalid '"hello"' 214 | invalid '"hello' 215 | invalid '"hi"' 216 | valid [ 1 , 2 , 3 ] 217 | invalid nil 218 | invalid fals 219 | invalid falsify 220 | invalid falsetto 221 | invalid truism 222 | invalid {"key" 223 | invalid {"key","key2":value} 224 | invalid "\u0000" 225 | -------------------------------------------------------------------------------- /vendor/ccan/json/test/test-strings-reencoded: -------------------------------------------------------------------------------- 1 | "￾" 2 | "￿" 3 | "" 4 | [] 5 | {} 6 | 0.5 7 | {"1":{}} 8 | {"1":2} 9 | {"1":2,"2.5":[3,4,{},{"5":["6"]}]} 10 | {"1":2,"2.5":[3,4,{},{"5":["6"],"7":[8]}]} 11 | 1234 12 | -1234 13 | {"1":2,"3":4} 14 | 1.23456e+144 15 | 1.23456e-140 16 | 1.23456e+144 17 | "1 " 18 | "1 1" 19 | 2 20 | 3 21 | "3" 22 | [3] 23 | 32 24 | [3,[4]] 25 | [3,[4,[5]]] 26 | [3,[4,[5],6]] 27 | [3,[4,[5],6],7] 28 | [3,[4,[5],6],7,8] 29 | [3,[4,[5],6],7,8,9] 30 | 30 31 | [7] 32 | [7] 33 | [7] 34 | "hello" 35 | ["hello"] 36 | ["hello","bye"] 37 | ["hello","bye\n"] 38 | ["hello","bye\n\r\t"] 39 | ["hello","bye\n\r\t\b"] 40 | ["hello","bye\n\r\t\b",true] 41 | ["hello","bye\n\r\t\b",true,false] 42 | ["hello","bye\n\r\t\b",true,false,null] 43 | {"hello":true} 44 | {"hello":true,"bye":false} 45 | {"hello":true,"bye":false,"foo":["one","two","three"]} 46 | "hi" 47 | ["hi"] 48 | ["hi","bye"] 49 | {"hi":"bye"} 50 | ["hi","bye",3] 51 | ["hi","bye[",3] 52 | "\u0007" 53 | "\b" 54 | "\t" 55 | "\u0010" 56 | " " 57 | "က0" 58 | "ሴ" 59 | "香9" 60 | "𐀀" 61 | "𐀀" 62 | "𝄞" 63 | "􏿿" 64 | "�" 65 | "￿" 66 | [32,1] 67 | "𐀀" 68 | "\n" 69 | "hello" 70 | "hello\tworld" 71 | "hello" 72 | "hello\n" 73 | "hello" 74 | 3 75 | 0.3 76 | 30000 77 | 3e-06 78 | 30000 79 | "hello" 80 | -3 81 | -3.1 82 | 0.5 83 | "\"" 84 | "\"3.5" 85 | "\"." 86 | "\"....." 87 | ["\"\"\"\"",0.5] 88 | ["\".5",".5\"",0.5] 89 | "'" 90 | [1,2,3] 91 | -------------------------------------------------------------------------------- /winrc/alert.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/alert.ico -------------------------------------------------------------------------------- /winrc/combined.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/combined.ico -------------------------------------------------------------------------------- /winrc/dnssec-trigger64.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/dnssec-trigger64.png -------------------------------------------------------------------------------- /winrc/gen_msg.bin: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/gen_msg.bin -------------------------------------------------------------------------------- /winrc/gen_msg.mc: -------------------------------------------------------------------------------- 1 | ; for dnssec-trigger 2 | ; severity default Success Informational Warning Error 3 | 4 | ; .bin file created with: 5 | ; "/c/Program Files/Microsoft SDKs/Windows/v6.1/Bin/mc" -c gen_msg.mc 6 | ; mv MSG00001.bin gen_msg.bin 7 | ; rm gen_msg.h 8 | ; and pasted contents of gen_msg.rc into rsrc_bla.rc 9 | 10 | FacilityNames=(Server=0x1) 11 | MessageIdTypeDef=DWORD 12 | 13 | MessageID=0x1 14 | Severity=Success 15 | Facility=Server 16 | SymbolicName=MSG_GENERIC_SUCCESS 17 | Language=English 18 | %1 19 | . 20 | 21 | MessageID=0x2 22 | Severity=Informational 23 | Facility=Server 24 | SymbolicName=MSG_GENERIC_INFO 25 | Language=English 26 | %1 27 | . 28 | 29 | MessageID=0x3 30 | Severity=Warning 31 | Facility=Server 32 | SymbolicName=MSG_GENERIC_WARN 33 | Language=English 34 | %1 35 | . 36 | 37 | MessageID=0x4 38 | Severity=Error 39 | Facility=Server 40 | SymbolicName=MSG_GENERIC_ERR 41 | Language=English 42 | %1 43 | . 44 | 45 | -------------------------------------------------------------------------------- /winrc/gtkrc: -------------------------------------------------------------------------------- 1 | # this is based on the Mist scheme from gtk-engines-2.10 2 | # it therefore has the same open-source license as that file. 3 | # it has been modified heavily. 4 | 5 | gtk-color-scheme = 6 | "bg_color:#eaeaea\nfg_color:#000\nbase_color:#fff\ntext_color:#000\nselected_fg_color:#fff\nselected_bg_color:#729fcf" 7 | 8 | style "default" 9 | { 10 | fg[NORMAL] = @fg_color 11 | fg[ACTIVE] = @fg_color 12 | fg[INSENSITIVE] = mix (0.4, @fg_color, shade (0.85, @bg_color)) #shaded to bg[INSENSITIVE] 13 | 14 | fg[PRELIGHT] = @fg_color 15 | fg[SELECTED] = @selected_fg_color 16 | 17 | bg[ACTIVE] = shade (0.9, @bg_color) 18 | bg[NORMAL] = @bg_color 19 | bg[INSENSITIVE] = shade (0.95, @bg_color) 20 | bg[PRELIGHT] = shade (1.03, @bg_color) 21 | bg[SELECTED] = @selected_bg_color 22 | 23 | base[NORMAL] = @base_color 24 | base[ACTIVE] = shade (0.9, @selected_bg_color) 25 | base[INSENSITIVE] = @base_color 26 | base[PRELIGHT] = @bg_color 27 | base[SELECTED] = @selected_bg_color 28 | 29 | text[NORMAL] = @text_color 30 | text[ACTIVE] = @text_color 31 | text[PRELIGHT] = @text_color 32 | text[SELECTED] = @selected_fg_color 33 | text[INSENSITIVE] = mix (0.5, @text_color, @base_color) 34 | 35 | 36 | GtkRange::trough_border = 0 37 | GtkRange::slider_width = 15 38 | GtkRange::stepper_size = 15 39 | 40 | GtkScrollbar::min_slider_length = 15 41 | GtkCheckButton::indicator_size=10 42 | GtkCheckMenuItem::indicator_size=10 43 | GtkRadioButton::indicator_size=12 44 | 45 | GtkNotebook::tab_vborder = 1 46 | GtkNotebook::tab_hborder = 1 47 | xthickness = 1 48 | ythickness = 1 49 | 50 | GtkMenu::horizontal_padding=0 51 | GtkMenu::vertical_padding=0 52 | 53 | #engine "mist" # no need to load a binary engine. 54 | #{ 55 | #} 56 | } 57 | 58 | style "button" 59 | { 60 | bg[PRELIGHT] = "#ddddff" 61 | GtkWidget::focus_line_width = 1 62 | } 63 | 64 | style "menuitem" 65 | { 66 | ythickness = 2 67 | xthickness = 2 68 | #text[PRELIGHT] = "#ffffff" 69 | #fg[PRELIGHT] = "#ffffff" 70 | #bg[PRELIGHT] = shade (0.8, @bg_color) 71 | bg[PRELIGHT] = "#ddddff" 72 | GtkMenuItem::selected_shadow_type=GTK_SHADOW_ETCHED_IN 73 | } 74 | 75 | style "menu" 76 | { 77 | ythickness = 2 78 | xthickness = 2 79 | } 80 | 81 | class "GtkWidget" style "default" 82 | class "GtkMenu" style "menu" 83 | class "GtkButton" style "button" 84 | class "*MenuItem*" style "menuitem" 85 | 86 | widget_class "*MenuItem*" style "menuitem" 87 | widget_class "*.GtkImageMenuItem.*" style "menuitem" 88 | widget_class "*.GtkAccelMenuItem.*" style "menuitem" 89 | widget_class "*.GtkRadioMenuItem.*" style "menuitem" 90 | widget_class "*.GtkCheckMenuItem.*" style "menuitem" 91 | widget_class "*.GtkMenu.*" style "menuitem" 92 | 93 | -------------------------------------------------------------------------------- /winrc/install.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/install.ico -------------------------------------------------------------------------------- /winrc/netlist.h: -------------------------------------------------------------------------------- 1 | /* 2 | * winrc/netlist.h - windows DHCP network listing service for dnssec trigger 3 | * 4 | * Copyright (c) 2011, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file waits for a network change then detects the networks that 40 | * exist. Looksup the DHCPprovided nameserver IPs from the registry and 41 | * informs the dnssec-triggerdaemon about it. 42 | */ 43 | #ifndef NETLIST_H 44 | #define NETLIST_H 45 | struct svr; 46 | 47 | /** callback from netlist */ 48 | void netlist_change_cb(int fd, short ev, void* arg); 49 | /** Start the netlist, adds event callback to the eventbase */ 50 | void netlist_start(struct svr* svr); 51 | /** Stop netlist, removes event. */ 52 | void netlist_stop(void); 53 | 54 | #endif /* NETLIST_H */ 55 | -------------------------------------------------------------------------------- /winrc/panel.manifest: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | dnssec-trigger user program 6 | 7 | 8 | 9 | 10 | 13 | 14 | 15 | 16 | 17 | 18 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /winrc/proc.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/proc.dll -------------------------------------------------------------------------------- /winrc/proc_dll_src/Processes.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/proc_dll_src/Processes.dll -------------------------------------------------------------------------------- /winrc/proc_dll_src/exdll.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "exdll.h" 3 | 4 | HINSTANCE g_hInstance; 5 | 6 | HWND g_hwndParent; 7 | 8 | void __declspec(dllexport) myFunction(HWND hwndParent, int string_size, 9 | char *variables, stack_t **stacktop) 10 | { 11 | g_hwndParent=hwndParent; 12 | 13 | EXDLL_INIT(); 14 | 15 | 16 | // note if you want parameters from the stack, pop them off in order. 17 | // i.e. if you are called via exdll::myFunction file.dat poop.dat 18 | // calling popstring() the first time would give you file.dat, 19 | // and the second time would give you poop.dat. 20 | // you should empty the stack of your parameters, and ONLY your 21 | // parameters. 22 | 23 | // do your stuff here 24 | { 25 | char buf[1024]; 26 | wsprintf(buf,"$0=%s\n",getuservariable(INST_0)); 27 | MessageBox(g_hwndParent,buf,0,MB_OK); 28 | } 29 | } 30 | 31 | 32 | 33 | BOOL WINAPI _DllMainCRTStartup(HANDLE hInst, ULONG ul_reason_for_call, LPVOID lpReserved) 34 | { 35 | g_hInstance=(HINSTANCE)hInst; 36 | return TRUE; 37 | } 38 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/exdll.h: -------------------------------------------------------------------------------- 1 | #ifndef _EXDLL_H_ 2 | #define _EXDLL_H_ 3 | 4 | 5 | 6 | 7 | 8 | // 9 | // only include this file from one place in your DLL. 10 | // (it is all static, if you use it in two places it will fail) 11 | // 12 | #define EXDLL_INIT() { \ 13 | g_stringsize = string_size; \ 14 | g_stacktop = stacktop; \ 15 | g_variables = variables; } 16 | 17 | 18 | 19 | 20 | // 21 | // For page showing plug-ins 22 | // 23 | #define WM_NOTIFY_OUTER_NEXT (WM_USER+0x8) 24 | #define WM_NOTIFY_CUSTOM_READY (WM_USER+0xd) 25 | #define NOTIFY_BYE_BYE 'x' 26 | 27 | typedef struct _stack_t 28 | { 29 | struct _stack_t *next; 30 | char text[1]; // this should be the length of string_size 31 | } stack_t; 32 | 33 | 34 | static unsigned int g_stringsize; 35 | static stack_t **g_stacktop; 36 | static char *g_variables; 37 | 38 | enum 39 | { 40 | INST_0, // $0 41 | INST_1, // $1 42 | INST_2, // $2 43 | INST_3, // $3 44 | INST_4, // $4 45 | INST_5, // $5 46 | INST_6, // $6 47 | INST_7, // $7 48 | INST_8, // $8 49 | INST_9, // $9 50 | INST_R0, // $R0 51 | INST_R1, // $R1 52 | INST_R2, // $R2 53 | INST_R3, // $R3 54 | INST_R4, // $R4 55 | INST_R5, // $R5 56 | INST_R6, // $R6 57 | INST_R7, // $R7 58 | INST_R8, // $R8 59 | INST_R9, // $R9 60 | INST_CMDLINE, // $CMDLINE 61 | INST_INSTDIR, // $INSTDIR 62 | INST_OUTDIR, // $OUTDIR 63 | INST_EXEDIR, // $EXEDIR 64 | INST_LANG, // $LANGUAGE 65 | __INST_LAST 66 | }; 67 | 68 | 69 | 70 | 71 | 72 | // 73 | // utility functions (not required but often useful) 74 | // 75 | static int popstring( char *str ) 76 | { 77 | stack_t *th; 78 | 79 | 80 | if( !g_stacktop || 81 | !*g_stacktop ) 82 | return 1; 83 | 84 | th = (*g_stacktop); 85 | lstrcpy( str, th->text ); 86 | *g_stacktop = th->next; 87 | GlobalFree( (HGLOBAL)th ); 88 | 89 | return 0; 90 | } 91 | 92 | 93 | 94 | 95 | static void pushstring( char *str ) 96 | { 97 | stack_t *th; 98 | 99 | 100 | if( !g_stacktop ) 101 | return; 102 | 103 | th = (stack_t*)GlobalAlloc( GPTR, sizeof(stack_t) + g_stringsize ); 104 | lstrcpyn( th->text, str, g_stringsize ); 105 | th->next = *g_stacktop; 106 | *g_stacktop = th; 107 | } 108 | 109 | 110 | 111 | 112 | 113 | static char *getuservariable( int varnum ) 114 | { 115 | if( varnum < 0 || 116 | varnum >= __INST_LAST ) 117 | return NULL; 118 | 119 | return (g_variables + varnum*g_stringsize); 120 | } 121 | 122 | 123 | 124 | 125 | 126 | static void setuservariable( int varnum, char *var ) 127 | { 128 | if( var != NULL && 129 | varnum >= 0 && 130 | varnum < __INST_LAST ) 131 | lstrcpy( g_variables + varnum*g_stringsize, var ); 132 | } 133 | 134 | 135 | 136 | #endif//_EXDLL_H_ -------------------------------------------------------------------------------- /winrc/proc_dll_src/license.rtf: -------------------------------------------------------------------------------- 1 | {\rtf1\ansi\ansicpg1252\uc1\deff0\stshfdbch0\stshfloch0\stshfhich0\stshfbi0\deflang1033\deflangfe1033{\fonttbl{\f0\froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\f39\fswiss\fcharset0\fprq2{\*\panose 020b0604030504040204}Verdana;} 2 | {\f172\froman\fcharset238\fprq2 Times New Roman CE;}{\f173\froman\fcharset204\fprq2 Times New Roman Cyr;}{\f175\froman\fcharset161\fprq2 Times New Roman Greek;}{\f176\froman\fcharset162\fprq2 Times New Roman Tur;} 3 | {\f177\froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\f178\froman\fcharset178\fprq2 Times New Roman (Arabic);}{\f179\froman\fcharset186\fprq2 Times New Roman Baltic;}{\f180\froman\fcharset163\fprq2 Times New Roman (Vietnamese);} 4 | {\f562\fswiss\fcharset238\fprq2 Verdana CE;}{\f563\fswiss\fcharset204\fprq2 Verdana Cyr;}{\f565\fswiss\fcharset161\fprq2 Verdana Greek;}{\f566\fswiss\fcharset162\fprq2 Verdana Tur;}{\f569\fswiss\fcharset186\fprq2 Verdana Baltic;} 5 | {\f570\fswiss\fcharset163\fprq2 Verdana (Vietnamese);}}{\colortbl;\red0\green0\blue0;\red0\green0\blue255;\red0\green255\blue255;\red0\green255\blue0;\red255\green0\blue255;\red255\green0\blue0;\red255\green255\blue0;\red255\green255\blue255; 6 | \red0\green0\blue128;\red0\green128\blue128;\red0\green128\blue0;\red128\green0\blue128;\red128\green0\blue0;\red128\green128\blue0;\red128\green128\blue128;\red192\green192\blue192;}{\stylesheet{ 7 | \ql \li0\ri0\widctlpar\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \fs24\lang1033\langfe1033\cgrid\langnp1033\langfenp1033 \snext0 Normal;}{\*\cs10 \additive \ssemihidden Default Paragraph Font;}{\* 8 | \ts11\tsrowd\trftsWidthB3\trpaddl108\trpaddr108\trpaddfl3\trpaddft3\trpaddfb3\trpaddfr3\trcbpat1\trcfpat1\tscellwidthfts0\tsvertalt\tsbrdrt\tsbrdrl\tsbrdrb\tsbrdrr\tsbrdrdgl\tsbrdrdgr\tsbrdrh\tsbrdrv 9 | \ql \li0\ri0\widctlpar\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \fs20\lang1024\langfe1024\cgrid\langnp1024\langfenp1024 \snext11 \ssemihidden Normal Table;}{\*\cs15 \additive \ul\cf2 \sbasedon10 \styrsid7485074 Hyperlink;}} 10 | {\*\latentstyles\lsdstimax156\lsdlockeddef0}{\*\rsidtbl \rsid6712196\rsid7485074\rsid11352300\rsid15940516}{\*\generator Microsoft Word 11.0.5604;}{\info{\title Processes v1}{\author Hardwired}{\operator Hardwired}{\creatim\yr2004\mo12\dy12\hr23\min42} 11 | {\revtim\yr2004\mo12\dy12\hr23\min51}{\version2}{\edmins9}{\nofpages1}{\nofwords80}{\nofchars458}{\nofcharsws537}{\vern24689}}\widowctrl\ftnbj\aenddoc\noxlattoyen\expshrtn\noultrlspc\dntblnsbdb\nospaceforul\formshade\horzdoc\dgmargin\dghspace180 12 | \dgvspace180\dghorigin1800\dgvorigin1440\dghshow1\dgvshow1 13 | \jexpand\viewkind1\viewscale100\pgbrdrhead\pgbrdrfoot\splytwnine\ftnlytwnine\htmautsp\nolnhtadjtbl\useltbaln\alntblind\lytcalctblwd\lyttblrtgr\lnbrkrule\nobrkwrptbl\snaptogridincell\allowfieldendsel\wrppunct 14 | \asianbrkrule\rsidroot7485074\newtblstyruls\nogrowautofit \fet0\sectd \linex0\endnhere\sectlinegrid360\sectdefaultcl\sftnbj {\*\pnseclvl1\pnucrm\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl2\pnucltr\pnstart1\pnindent720\pnhang {\pntxta .}} 15 | {\*\pnseclvl3\pndec\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl4\pnlcltr\pnstart1\pnindent720\pnhang {\pntxta )}}{\*\pnseclvl5\pndec\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl6\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (} 16 | {\pntxta )}}{\*\pnseclvl7\pnlcrm\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl8\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl9\pnlcrm\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}\pard\plain 17 | \qj \li0\ri0\widctlpar\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0\pararsid7485074 \fs24\lang1033\langfe1033\cgrid\langnp1033\langfenp1033 {\b\f39\insrsid7485074\charrsid7485074 Processes v1.0}{\f39\insrsid7485074\charrsid7485074 .0.1 18 | \par }{\f39\fs20\insrsid7485074 19 | \par }\pard \qj \li0\ri0\widctlpar\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0\pararsid15940516 {\f39\fs20\insrsid15940516 This software binaries and source-code are free for any kind of use, including commercial use. }{ 20 | \f39\fs20\insrsid7485074\charrsid7485074 There is no restriction and no guaranty for using}{\f39\fs20\insrsid7485074\charrsid7485074 t}{\f39\fs20\insrsid7485074\charrsid7485074 his software}{\f39\fs20\insrsid7485074\charrsid7485074 and/or it 21 | s source-code. }{\f39\fs20\insrsid15940516 22 | \par I}{\f39\fs20\insrsid7485074\charrsid7485074 f you use the plug}{\f39\fs20\insrsid7485074\charrsid7485074 -}{\f39\fs20\insrsid7485074\charrsid7485074 in }{\f39\fs20\insrsid7485074\charrsid7485074 and/}{\f39\fs20\insrsid7485074\charrsid7485074 or it}{ 23 | \f39\fs20\insrsid7485074\charrsid7485074 s}{\f39\fs20\insrsid7485074\charrsid7485074 source-code, I would }{\f39\fs20\insrsid7485074\charrsid7485074 appreciate }{\f39\fs20\insrsid7485074\charrsid7485074 if my name is mentioned.}{ 24 | \f39\fs20\insrsid7485074\charrsid7485074 25 | \par }\pard \qj \li0\ri0\widctlpar\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0\pararsid7485074 {\f39\fs20\insrsid7485074\charrsid7485074 26 | \par }{\b\f39\fs20\insrsid7485074\charrsid7485074 Andrei Ciubotaru [Hardwired] 27 | \par }{\f39\fs20\insrsid7485074\charrsid7485074 Lead Developer ICode&Ideas SRL (}{\field\flddirty{\*\fldinst {\f39\fs20\insrsid7485074\charrsid7485074 HYPERLINK "http://www.icode.ro/" }{\f39\fs20\insrsid7485074\charrsid7485074 {\*\datafield 28 | 00d0c9ea79f9bace118c8200aa004ba90b02000000170000001500000068007400740070003a002f002f007700770077002e00690063006f00640065002e0072006f002f000000e0c9ea79f9bace118c8200aa004ba90b2a00000068007400740070003a002f002f007700770077002e00690063006f00640065002e007200 29 | 6f002f000000}}}{\fldrslt {\cs15\f39\fs20\ul\cf2\insrsid7485074\charrsid7485074 http://www.icode.ro/}}}{\f39\fs20\insrsid7485074\charrsid7485074 ) 30 | \par }{\field{\*\fldinst {\f39\fs20\insrsid7485074 HYPERLINK "hardwiredteks@gmail.com" }{\f39\fs20\insrsid15940516\charrsid7485074 {\*\datafield 31 | 00d0c9ea79f9bace118c8200aa004ba90b02000000010000000303000000000000c00000000000004600001800000068617264776972656474656b7340676d61696c2e636f6d00ffffadde000000000000000000000000000000000000000000000000}}}{\fldrslt { 32 | \cs15\f39\fs20\ul\cf2\insrsid7485074\charrsid7485074 hardwiredteks@gmail.com}}}{\f39\fs20\insrsid7485074\charrsid7485074 , }{\field{\*\fldinst {\f39\fs20\insrsid7485074 HYPERLINK "hardwired@icode.ro" }{\f39\fs20\insrsid15940516\charrsid7485074 33 | {\*\datafield 00d0c9ea79f9bace118c8200aa004ba90b02000000010000000303000000000000c0000000000000460000130000006861726477697265644069636f64652e726f00ffffadde000000000000000000000000000000000000000000000000}}}{\fldrslt { 34 | \cs15\f39\fs20\ul\cf2\insrsid7485074\charrsid7485074 hardwired@icode.ro}}}{\f39\fs20\insrsid7485074\charrsid7485074 35 | \par }} -------------------------------------------------------------------------------- /winrc/proc_dll_src/make.sh: -------------------------------------------------------------------------------- 1 | #i686-pc-mingw32-gcc processes.cpp -o bla.dll -mdll -nodefaultlibs -luser32 -lgcc -lmoldname -lmingw32 -lmsvcrt -lkernel32 2 | echo gcc 3 | i686-pc-mingw32-gcc -g -O2 processes.c -o proc.dll -mdll -nostartfiles -e __DllMainCRTStartup@12 4 | ls -l proc.dll 5 | echo strip 6 | i686-pc-mingw32-strip proc.dll 7 | ls -l proc.dll 8 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/proc.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/proc_dll_src/proc.dll -------------------------------------------------------------------------------- /winrc/proc_dll_src/processes.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | 4 | 5 | 6 | 7 | //------------------------------------------------------------------------------------------- 8 | // PSAPI function pointers 9 | typedef BOOL (WINAPI *lpfEnumProcesses) ( DWORD *, DWORD, DWORD * ); 10 | typedef BOOL (WINAPI *lpfEnumProcessModules) ( HANDLE, HMODULE *, DWORD, LPDWORD ); 11 | typedef DWORD (WINAPI *lpfGetModuleBaseName) ( HANDLE, HMODULE, LPTSTR, DWORD ); 12 | typedef BOOL (WINAPI *lpfEnumDeviceDrivers) ( LPVOID *, DWORD, LPDWORD ); 13 | typedef BOOL (WINAPI *lpfGetDeviceDriverBaseName)( LPVOID, LPTSTR, DWORD ); 14 | 15 | 16 | 17 | 18 | 19 | 20 | //------------------------------------------------------------------------------------------- 21 | // Internal use routines 22 | bool LoadPSAPIRoutines( void ); 23 | bool FreePSAPIRoutines( void ); 24 | 25 | bool FindProc( char *szProcess ); 26 | bool KillProc( char *szProcess ); 27 | 28 | bool FindDev( char *szDriverName ); 29 | 30 | 31 | 32 | 33 | 34 | //------------------------------------------------------------------------------------------- 35 | // Exported routines 36 | __declspec(dllexport) void FindProcess( HWND hwndParent, 37 | int string_size, 38 | char *variables, 39 | stack_t **stacktop ); 40 | 41 | __declspec(dllexport) void KillProcess( HWND hwndParent, 42 | int string_size, 43 | char *variables, 44 | stack_t **stacktop ); 45 | 46 | __declspec(dllexport) void FindDevice( HWND hwndParent, 47 | int string_size, 48 | char *variables, 49 | stack_t **stacktop ); 50 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/processes.rc: -------------------------------------------------------------------------------- 1 | // Microsoft Visual C++ generated resource script. 2 | // 3 | #include "resource.h" 4 | 5 | #define APSTUDIO_READONLY_SYMBOLS 6 | ///////////////////////////////////////////////////////////////////////////// 7 | // 8 | // Generated from the TEXTINCLUDE 2 resource. 9 | // 10 | #include "afxres.h" 11 | 12 | ///////////////////////////////////////////////////////////////////////////// 13 | #undef APSTUDIO_READONLY_SYMBOLS 14 | 15 | ///////////////////////////////////////////////////////////////////////////// 16 | // English (U.S.) resources 17 | 18 | #if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU) 19 | #ifdef _WIN32 20 | LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US 21 | #pragma code_page(1252) 22 | #endif //_WIN32 23 | 24 | #ifdef APSTUDIO_INVOKED 25 | ///////////////////////////////////////////////////////////////////////////// 26 | // 27 | // TEXTINCLUDE 28 | // 29 | 30 | 1 TEXTINCLUDE 31 | BEGIN 32 | "resource.h\0" 33 | END 34 | 35 | 2 TEXTINCLUDE 36 | BEGIN 37 | "#include ""afxres.h""\r\n" 38 | "\0" 39 | END 40 | 41 | 3 TEXTINCLUDE 42 | BEGIN 43 | "\r\n" 44 | "\0" 45 | END 46 | 47 | #endif // APSTUDIO_INVOKED 48 | 49 | 50 | ///////////////////////////////////////////////////////////////////////////// 51 | // 52 | // Version 53 | // 54 | 55 | VS_VERSION_INFO VERSIONINFO 56 | FILEVERSION 1,0,0,1 57 | PRODUCTVERSION 1,0,0,1 58 | FILEFLAGSMASK 0x17L 59 | #ifdef _DEBUG 60 | FILEFLAGS 0x1L 61 | #else 62 | FILEFLAGS 0x0L 63 | #endif 64 | FILEOS 0x4L 65 | FILETYPE 0x2L 66 | FILESUBTYPE 0x0L 67 | BEGIN 68 | BLOCK "StringFileInfo" 69 | BEGIN 70 | BLOCK "040904b0" 71 | BEGIN 72 | VALUE "Comments", "NSIS Plug-in for Windows process management. Only WinNT, Win2K, WinXP and Win2003 Server supported." 73 | VALUE "CompanyName", "Andrei Ciubotaru [Hardwired]" 74 | VALUE "FileDescription", "Windows Processes Management" 75 | VALUE "FileVersion", "1, 0, 0, 1" 76 | VALUE "InternalName", "Processes" 77 | VALUE "LegalCopyright", "Copyright (c) 2004 Hardwired. No rights reserved." 78 | VALUE "OriginalFilename", "Processes.dll" 79 | VALUE "ProductName", "Processes" 80 | VALUE "ProductVersion", "1, 0, 0, 1" 81 | END 82 | END 83 | BLOCK "VarFileInfo" 84 | BEGIN 85 | VALUE "Translation", 0x409, 1200 86 | END 87 | END 88 | 89 | #endif // English (U.S.) resources 90 | ///////////////////////////////////////////////////////////////////////////// 91 | 92 | 93 | 94 | #ifndef APSTUDIO_INVOKED 95 | ///////////////////////////////////////////////////////////////////////////// 96 | // 97 | // Generated from the TEXTINCLUDE 3 resource. 98 | // 99 | 100 | 101 | ///////////////////////////////////////////////////////////////////////////// 102 | #endif // not APSTUDIO_INVOKED 103 | 104 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/processes.sln: -------------------------------------------------------------------------------- 1 | Microsoft Visual Studio Solution File, Format Version 10.00 2 | # Visual Studio 2008 3 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "processes", "processes.vcproj", "{3438467F-A719-46DC-93E5-137A8B691727}" 4 | EndProject 5 | Global 6 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 7 | Debug|Win32 = Debug|Win32 8 | Release|Win32 = Release|Win32 9 | EndGlobalSection 10 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 11 | {3438467F-A719-46DC-93E5-137A8B691727}.Debug|Win32.ActiveCfg = Debug|Win32 12 | {3438467F-A719-46DC-93E5-137A8B691727}.Debug|Win32.Build.0 = Debug|Win32 13 | {3438467F-A719-46DC-93E5-137A8B691727}.Release|Win32.ActiveCfg = Release|Win32 14 | {3438467F-A719-46DC-93E5-137A8B691727}.Release|Win32.Build.0 = Release|Win32 15 | EndGlobalSection 16 | GlobalSection(SolutionProperties) = preSolution 17 | HideSolutionNode = FALSE 18 | EndGlobalSection 19 | EndGlobal 20 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/processes.suo: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/proc_dll_src/processes.suo -------------------------------------------------------------------------------- /winrc/proc_dll_src/processes.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/proc_dll_src/processes.txt -------------------------------------------------------------------------------- /winrc/proc_dll_src/readme.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/proc_dll_src/readme.txt -------------------------------------------------------------------------------- /winrc/proc_dll_src/resource.h: -------------------------------------------------------------------------------- 1 | //{{NO_DEPENDENCIES}} 2 | // Microsoft Visual C++ generated include file. 3 | // Used by processes.rc 4 | // 5 | 6 | // Next default values for new objects 7 | // 8 | #ifdef APSTUDIO_INVOKED 9 | #ifndef APSTUDIO_READONLY_SYMBOLS 10 | #define _APS_NEXT_RESOURCE_VALUE 101 11 | #define _APS_NEXT_COMMAND_VALUE 40001 12 | #define _APS_NEXT_CONTROL_VALUE 1001 13 | #define _APS_NEXT_SYMED_VALUE 101 14 | #endif 15 | #endif 16 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/stdafx.cpp: -------------------------------------------------------------------------------- 1 | // stdafx.cpp : source file that includes just the standard includes 2 | // KillProcDLL.pch will be the pre-compiled header 3 | // stdafx.obj will contain the pre-compiled type information 4 | 5 | #include "stdafx.h" 6 | 7 | // TODO: reference any additional headers you need in STDAFX.H 8 | // and not in this file 9 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/stdafx.h: -------------------------------------------------------------------------------- 1 | #if !defined(AFX_STDAFX_H__780690DC_E128_403D_BC07_780D1B2CC101__INCLUDED_) 2 | #define AFX_STDAFX_H__780690DC_E128_403D_BC07_780D1B2CC101__INCLUDED_ 3 | 4 | #if _MSC_VER > 1000 5 | #pragma once 6 | #endif // _MSC_VER > 1000 7 | 8 | #define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers 9 | #define NOGDI 10 | 11 | #include 12 | 13 | #include // String management... 14 | #include 15 | #include 16 | 17 | #ifdef BORLANDC 18 | #include 19 | #include 20 | #endif 21 | 22 | //To make it a NSIS Plug-In 23 | #include "exdll.h" 24 | 25 | //{{AFX_INSERT_LOCATION}} 26 | // Microsoft Visual C++ will insert additional declarations immediately before the previous line. 27 | 28 | #endif // !defined(AFX_STDAFX_H__780690DC_E128_403D_BC07_780D1B2CC101__INCLUDED_) 29 | -------------------------------------------------------------------------------- /winrc/proc_dll_src/stdafx_orig.h: -------------------------------------------------------------------------------- 1 | // stdafx.h : include file for standard system include files, 2 | // or project specific include files that are used frequently, but 3 | // are changed infrequently 4 | // 5 | 6 | #if !defined(AFX_STDAFX_H__780690DC_E128_403D_BC07_780D1B2CC101__INCLUDED_) 7 | #define AFX_STDAFX_H__780690DC_E128_403D_BC07_780D1B2CC101__INCLUDED_ 8 | 9 | #if _MSC_VER > 1000 10 | #pragma once 11 | #endif // _MSC_VER > 1000 12 | 13 | #define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers 14 | 15 | #include 16 | 17 | #include // String management... 18 | 19 | //From exam28.cpp 20 | #include 21 | //#include 22 | 23 | #ifdef BORLANDC 24 | #include 25 | #include 26 | #endif 27 | 28 | //To make it a NSIS Plug-In 29 | #include "exdll.h" 30 | 31 | //{{AFX_INSERT_LOCATION}} 32 | // Microsoft Visual C++ will insert additional declarations immediately before the previous line. 33 | 34 | #endif // !defined(AFX_STDAFX_H__780690DC_E128_403D_BC07_780D1B2CC101__INCLUDED_) 35 | -------------------------------------------------------------------------------- /winrc/rsrc_control.rc: -------------------------------------------------------------------------------- 1 | /* 2 | dnssec-trigger-control resource file for windows. For use with windres 3 | */ 4 | #include "winver.h" 5 | #include "config.h" 6 | 7 | 1 ICON "winrc/combined.ico" 8 | 9 | 1 VERSIONINFO 10 | FILEVERSION RSRC_PACKAGE_VERSION 11 | PRODUCTVERSION RSRC_PACKAGE_VERSION 12 | FILEFLAGSMASK 0 13 | FILEFLAGS 0 14 | FILEOS VOS__WINDOWS32 15 | FILETYPE VFT_APP 16 | FILESUBTYPE 0 17 | BEGIN 18 | BLOCK "StringFileInfo" 19 | BEGIN 20 | BLOCK "040904E4" 21 | BEGIN 22 | VALUE "CompanyName", "NLnet Labs" 23 | VALUE "FileDescription", "DnssecTrigger Remote Control Tool" 24 | VALUE "FileVersion", PACKAGE_VERSION 25 | VALUE "InternalName", "dnssec-trigger-control" 26 | VALUE "OriginalFilename", "dnssec-trigger-control.exe" 27 | VALUE "ProductName", "DnssecTrigger" 28 | VALUE "ProductVersion", PACKAGE_VERSION 29 | VALUE "LegalCopyright", "(C) 2011 NLnet Labs. Source is BSD licensed." 30 | END 31 | END 32 | BLOCK "VarFileInfo" 33 | BEGIN 34 | /* English(409), windows ANSI codepage (1252) */ 35 | VALUE "Translation", 0x409, 0x1252 36 | END 37 | END 38 | /* vista user access as invoker */ 39 | 1 RT_MANIFEST "winrc/vista_user.manifest" 40 | -------------------------------------------------------------------------------- /winrc/rsrc_keygen.rc: -------------------------------------------------------------------------------- 1 | /* 2 | dnssec-trigger-keygen resource file for windows. For use with windres 3 | */ 4 | #include "winver.h" 5 | #include "config.h" 6 | 7 | 1 ICON "winrc/combined.ico" 8 | 9 | 1 VERSIONINFO 10 | FILEVERSION RSRC_PACKAGE_VERSION 11 | PRODUCTVERSION RSRC_PACKAGE_VERSION 12 | FILEFLAGSMASK 0 13 | FILEFLAGS 0 14 | FILEOS VOS__WINDOWS32 15 | FILETYPE VFT_APP 16 | FILESUBTYPE 0 17 | BEGIN 18 | BLOCK "StringFileInfo" 19 | BEGIN 20 | BLOCK "040904E4" 21 | BEGIN 22 | VALUE "CompanyName", "NLnet Labs" 23 | VALUE "FileDescription", "DnssecTrigger access key gen" 24 | VALUE "FileVersion", PACKAGE_VERSION 25 | VALUE "InternalName", "dnssec-trigger-keygen" 26 | VALUE "OriginalFilename", "dnssec-trigger-keygen.exe" 27 | VALUE "ProductName", "DnssecTrigger" 28 | VALUE "ProductVersion", PACKAGE_VERSION 29 | VALUE "LegalCopyright", "(C) 2011 NLnet Labs. Source is BSD licensed." 30 | END 31 | END 32 | BLOCK "VarFileInfo" 33 | BEGIN 34 | /* English(409), windows ANSI codepage (1252) */ 35 | VALUE "Translation", 0x409, 0x1252 36 | END 37 | END 38 | /* vista user access as invoker */ 39 | 1 RT_MANIFEST "winrc/vista_user.manifest" 40 | -------------------------------------------------------------------------------- /winrc/rsrc_panel.rc: -------------------------------------------------------------------------------- 1 | /* 2 | dnssec-trigger-control resource file for windows. For use with windres 3 | */ 4 | #include "winver.h" 5 | #include "config.h" 6 | 7 | 1 ICON "winrc/combined.ico" 8 | 9 | 1 VERSIONINFO 10 | FILEVERSION RSRC_PACKAGE_VERSION 11 | PRODUCTVERSION RSRC_PACKAGE_VERSION 12 | FILEFLAGSMASK 0 13 | FILEFLAGS 0 14 | FILEOS VOS__WINDOWS32 15 | FILETYPE VFT_APP 16 | FILESUBTYPE 0 17 | BEGIN 18 | BLOCK "StringFileInfo" 19 | BEGIN 20 | BLOCK "040904E4" 21 | BEGIN 22 | VALUE "CompanyName", "NLnet Labs" 23 | VALUE "FileDescription", "DnssecTrigger tray panel" 24 | VALUE "FileVersion", PACKAGE_VERSION 25 | VALUE "InternalName", "dnssec-trigger-panel" 26 | VALUE "OriginalFilename", "dnssec-trigger-panel.exe" 27 | VALUE "ProductName", "DnssecTrigger" 28 | VALUE "ProductVersion", PACKAGE_VERSION 29 | VALUE "LegalCopyright", "(C) 2011 NLnet Labs. Source is BSD licensed." 30 | END 31 | END 32 | BLOCK "VarFileInfo" 33 | BEGIN 34 | /* English(409), windows ANSI codepage (1252) */ 35 | VALUE "Translation", 0x409, 0x1252 36 | END 37 | END 38 | /* vista user access as invoker */ 39 | 1 RT_MANIFEST "winrc/panel.manifest" 40 | -------------------------------------------------------------------------------- /winrc/rsrc_triggerd.rc: -------------------------------------------------------------------------------- 1 | /* 2 | dnssec-triggerd resource file for windows. For use with windres 3 | */ 4 | #include "winver.h" 5 | #include "config.h" 6 | 7 | 1 ICON "winrc/combined.ico" 8 | /* 9 | 1 ICON "winrc/dnssec-trigger64.ico" 10 | 2 ICON "winrc/dnssec-trigger48.ico" 11 | 3 ICON "winrc/dnssec-trigger32.ico" 12 | 4 ICON "winrc/dnssec-trigger16.ico" 13 | */ 14 | 15 | 1 VERSIONINFO 16 | FILEVERSION RSRC_PACKAGE_VERSION 17 | PRODUCTVERSION RSRC_PACKAGE_VERSION 18 | FILEFLAGSMASK 0 19 | FILEFLAGS 0 20 | FILEOS VOS__WINDOWS32 21 | FILETYPE VFT_APP 22 | FILESUBTYPE 0 23 | BEGIN 24 | BLOCK "StringFileInfo" 25 | BEGIN 26 | BLOCK "040904E4" 27 | BEGIN 28 | VALUE "CompanyName", "NLnet Labs" 29 | VALUE "FileDescription", "DnssecTrigger service" 30 | VALUE "FileVersion", PACKAGE_VERSION 31 | VALUE "InternalName", "dnssec-triggerd" 32 | VALUE "OriginalFilename", "dnssec-triggerd.exe" 33 | VALUE "ProductName", "DnssecTrigger" 34 | VALUE "ProductVersion", PACKAGE_VERSION 35 | VALUE "LegalCopyright", "(C) 2011 NLnet Labs. Source is BSD licensed." 36 | END 37 | END 38 | BLOCK "VarFileInfo" 39 | BEGIN 40 | /* English(409), windows ANSI codepage (1252) */ 41 | VALUE "Translation", 0x409, 0x1252 42 | END 43 | END 44 | 45 | /* error message formats */ 46 | LANGUAGE 0x9,0x1 47 | /* id=1 type=RT_MESSAGETABLE */ 48 | 1 11 "winrc/gen_msg.bin" 49 | 50 | /* vista administrator access, show UAC prompt */ 51 | 1 RT_MANIFEST "winrc/vista_admin.manifest" 52 | -------------------------------------------------------------------------------- /winrc/setup_left.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/setup_left.bmp -------------------------------------------------------------------------------- /winrc/setup_left_un.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/setup_left_un.bmp -------------------------------------------------------------------------------- /winrc/setup_top.bmp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/setup_top.bmp -------------------------------------------------------------------------------- /winrc/status.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/status.ico -------------------------------------------------------------------------------- /winrc/uninstall.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/NLnetLabs/dnssec-trigger/c8493ef4daaee7a8bed57f6722f92ff39f838937/winrc/uninstall.ico -------------------------------------------------------------------------------- /winrc/vista_admin.manifest: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | the dnssec-trigger service 6 | 7 | 8 | 9 | 10 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /winrc/vista_user.manifest: -------------------------------------------------------------------------------- 1 | 2 | 3 | 5 | dnssec-trigger user program 6 | 7 | 8 | 9 | 10 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /winrc/w_inst.h: -------------------------------------------------------------------------------- 1 | /* 2 | * winrc/w_inst.h - install and remove functions 3 | * 4 | * Copyright (c) 2009, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * Contains install and remove functions that manipulate the 40 | * windows services API and windows registry. 41 | */ 42 | 43 | #ifndef WINRC_W_INST_H 44 | #define WINRC_W_INST_H 45 | 46 | /** 47 | * Install service in servicecontrolmanager, setup registry 48 | * @param out: debug output printed here (errors). or NULL. 49 | * @param rename: if nonNULL this executable is not the .exe but this name. 50 | */ 51 | void wsvc_install(FILE* out, const char* rename); 52 | 53 | /** 54 | * Remove installed service from servicecontrolmanager, registry entries 55 | * @param out: debug output printed here (errors). or NULL. 56 | */ 57 | void wsvc_remove(FILE* out); 58 | 59 | /** 60 | * Start the service from servicecontrolmanager, tells OS to start daemon. 61 | * @param out: debug output printed here (errors). or NULL. 62 | */ 63 | void wsvc_rc_start(FILE* out); 64 | 65 | /** 66 | * Stop the service from servicecontrolmanager, tells OS to stop daemon. 67 | * @param out: debug output printed here (errors). or NULL. 68 | */ 69 | void wsvc_rc_stop(FILE* out); 70 | 71 | /** 72 | * Wait for a service to come to a full stop. 73 | * @param out: debug output printed here (errors). or NULL. 74 | * @param name: service name to wait for. 75 | */ 76 | void wsvc_rc_waitstop(FILE* out, const char* name); 77 | 78 | /** 79 | * Convert windows GetLastError() value to a neat string. 80 | * @param str: destination buffer 81 | * @param len: length of dest buffer 82 | * @param fixed: fixed text to prepend to string. 83 | * @param err: the GetLastError() value. 84 | */ 85 | void wsvc_err2str(char* str, size_t len, const char* fixed, DWORD err); 86 | 87 | #endif /* WINRC_W_INST_H */ 88 | -------------------------------------------------------------------------------- /winrc/win_svc.h: -------------------------------------------------------------------------------- 1 | /* 2 | * winrc/win_svc.h - windows services API implementation for dnssec-trigger 3 | * 4 | * Copyright (c) 2009, NLnet Labs. All rights reserved. 5 | * 6 | * This software is open source. 7 | * 8 | * Redistribution and use in source and binary forms, with or without 9 | * modification, are permitted provided that the following conditions 10 | * are met: 11 | * 12 | * Redistributions of source code must retain the above copyright notice, 13 | * this list of conditions and the following disclaimer. 14 | * 15 | * Redistributions in binary form must reproduce the above copyright notice, 16 | * this list of conditions and the following disclaimer in the documentation 17 | * and/or other materials provided with the distribution. 18 | * 19 | * Neither the name of the NLNET LABS nor the names of its contributors may 20 | * be used to endorse or promote products derived from this software without 21 | * specific prior written permission. 22 | * 23 | * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 24 | * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 25 | * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 26 | * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 27 | * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 28 | * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED 29 | * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 30 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF 31 | * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING 32 | * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS 33 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 34 | */ 35 | 36 | /** 37 | * \file 38 | * 39 | * This file contains functions to integrate with the windows services API. 40 | * This means it handles the commandline switches to install and remove 41 | * the service (via CreateService and DeleteService), it handles 42 | * the ServiceMain() main service entry point when started as a service, 43 | * and it handles the Handler[_ex]() to process requests to the service 44 | * (such as start and stop and status). 45 | */ 46 | 47 | #ifndef WINRC_WIN_SVC_H 48 | #define WINRC_WIN_SVC_H 49 | struct comm_base; 50 | 51 | /** service name for unbound (internal to ServiceManager) */ 52 | #define SERVICE_NAME "dnssectrigger" 53 | 54 | /** from gen_msg.h - success message record for windows message log */ 55 | #define MSG_GENERIC_SUCCESS ((DWORD)0x20010001L) 56 | /** from gen_msg.h - informational message record for windows message log */ 57 | #define MSG_GENERIC_INFO ((DWORD)0x60010002L) 58 | /** from gen_msg.h - warning message record for windows message log */ 59 | #define MSG_GENERIC_WARN ((DWORD)0xA0010003L) 60 | /** from gen_msg.h - error message record for windows message log */ 61 | #define MSG_GENERIC_ERR ((DWORD)0xE0010004L) 62 | 63 | /** 64 | * Handle commandline service for windows. 65 | * @param wopt: windows option string (install, remove, service). 66 | * @param cfgfile: configfile to open (default or passed with -c). 67 | * @param v: amount of commandline verbosity added with -v. 68 | * @param c: true if cfgfile was set by commandline -c option. 69 | */ 70 | void wsvc_command_option(const char* wopt, const char* cfgfile, int v, int c); 71 | 72 | /** 73 | * Setup lead worker events. 74 | */ 75 | void wsvc_setup_worker(struct comm_base* base); 76 | 77 | /** 78 | * Desetup lead worker events. 79 | */ 80 | void wsvc_desetup_worker(void); 81 | 82 | /** windows worker stop event callback handler */ 83 | void worker_win_stop_cb(int fd, short ev, void* arg); 84 | 85 | /** windows cron timer callback handler */ 86 | void wsvc_cron_cb(void* arg); 87 | 88 | /** 89 | * Obtain registry string (if it exists). 90 | * @param key: key string 91 | * @param name: name of value to fetch. 92 | * @return malloced string with the result or NULL if it did not 93 | * exist on an error (logged) was encountered. 94 | */ 95 | char* lookup_reg_str(const char* key, const char* name); 96 | 97 | /** 98 | * Obtain registry binary data (if it exists). 99 | * @param key: key string 100 | * @param name: name of value to fetch. 101 | * @param len: (returned value on success) length of the binary data. 102 | * @return malloced binary data with the result or NULL if it did not 103 | * exist on an error (logged) was encountered. 104 | */ 105 | uint8_t* lookup_reg_binary(const char* key, const char* name, size_t* len); 106 | 107 | /** log a windows GetLastError message */ 108 | void log_win_err(const char* str, DWORD err); 109 | 110 | /** 111 | * Run command, and wait for result. 112 | * @param cmd: the command and arguments. 113 | * @return: return code of the program. If -1, errno. 114 | */ 115 | int win_run_cmd(char* cmd); 116 | 117 | /** 118 | * Set resolver to use on windows 119 | * @param ip: list of ips with spaces. 120 | */ 121 | void win_set_resolv(char* ip); 122 | 123 | /** 124 | * Remove resolver entry 125 | */ 126 | void win_clear_resolv(void); 127 | 128 | /** sets NameServer in HKEY(registry space) to the arg(string or NULL) */ 129 | void enum_reg_set_nameserver(HKEY hk, void* arg); 130 | 131 | /** fetch unbound-control name from registry (or NULL), struped result */ 132 | char* get_registry_unbound_control(void); 133 | 134 | #endif /* WINRC_WIN_SVC_H */ 135 | --------------------------------------------------------------------------------