NETGEAR N750 (WNDR4300) fixes

The NETGEAR N750 (WNDR4300) SOHO WiFi router/gateway is a popular choice for 802.11a/b/g/n WiFi, but has some glaring security vulnerabilities that can allow anyone on the network (LAN-side including wireless) administrative (unauthenticated) access to the router or access to otherwise private data (keys to the WLAN from the guest network for example).

The firmware for this router is based on OpenWrt, with much of the custom source published publicly by NETGEAR.

A brief synopsis of some of the known vulnerabilities are:

  • Anyone on the LAN or the non-guest WLAN can enable an unauthenticated telnet interface with full access to the router.
  • Anyone on the LAN or the non-guest WLAN, or if remote administration is enabled also the WAN, can gain unauthenticated access to the administrative web interface.
  • Anyone on the LAN or the non-guest WLAN, or if remote administration is enabled also the WAN, can disable authentication to the administrative web interface without being authenticated.

There’s a more detailed article about some of these vulnerabilities on InfoWorld.

I’ll explain how I fixed some of these security vulnerabilities (without having to use one of the many custom firmwares such as dd-wrt) below.

Source of these vulnerabilities

The telnet server can simply be disabled, which solves problem #1.

The HTTP server (uhttpd) doesn’t perform any authentication at all on these devices, which is unfortunate because that’s one of the apps where the code is public.

Instead, requests are passed off to (closed source) net-cgi which performs authentication/authorization, exposes private methods to CGI scripts and runs/interprets CGI scripts or simply serves static pages (css/jpg/gif files are generally served directly from uhttpd though).

I’m not sure where the code for net-cgi is. Maybe it’s not open source, or I just can’t find it. There are probably a bunch more access control bypass issues here, but I don’t feel like taking the time to decompile the binary to find them…

net-cgi contains the code that ignores authentication/authorization if the page starts with BRS_ or contains unauth.cgi or securityquestions.cgi or if the hijack_process config setting is not 3 (and probably some other BS).

To get around these issues with the web administration interface I’ve just completely ditch all the BRS_* CGI scripts which aren’t useful to me and hacked uhttpd to strip out ‘unauth.cgi’ or ‘securityquestions.cgi’ strings in the URL of request prior to handing the request off to net-cgi.

It would seem to have been a better implementation to have a startup script generate an httpd.conf file based on various settings (read from /bin/config) and used the standard uhttpd authentication, than to have put authorization logic in net-cgi itself. This kind of thing is done for other services on the router.

Vulnerability: Full access to the router via telnet

The router allows unauthenticated telnet access to anyone on the LAN or non-guest WLAN via the telnetEnable tool.

Once telnet’d into the router, you have full visibility into all the data stored on the device (wifi passwords, web admin password, email passwords if your logs are emailed, etc).

Vulnerability: Access the administrative web interface unauthenticated

Making a web request to the router with “unauth.cgi” or “securityquestions.cgi” anywhere in the URL (including the query string) will allow you to access the page.

http://192.168.1.1/adv_index.htm?unauth.cgi or http://192.168.1.1/adv_index.htm?securityquestions.cgi (192.168.1.1 is the name or IP address of your router), and you can access that page.

Do the same with any of the other CGI pages (change the WiFi password for example) and you can have your way.

Vulnerability: Removing authentication in the web administration interface

Simply by hitting the web page http://192.168.1.1/BRS_02_genieHelp.html or http://192.168.1.1/BRS_03B_haveBackupFile_fileRestore.html (192.168.1.1 is the name or IP address of your router), the router will be put in a state where authentication is no longer required to administer the router via the web interface. And this change persists across router reboots. See this YouTube video for more details.

Once this web page has been accessed, you need to telnet in and modify a config setting (set hijack_process = 3 via /bin/config) in order for the router to require authentication for web administration again (which can again just simply be undone via hitting either of those BRS_*.html pages). After applying my patch below, you can just hit /BRS_fix.html to reset hijack_process to 3 without telnet access.

Rebuilding the firmware to close these holes

To remove telnet access and the bad BRS_*.html web pages, I rebuilt the firmware (on Fedora 20) removing that web page and the code that starts up the telnetEnable listener (and telnet daemon for completeness sake).

wget ftp://downloads.netgear.com/files/GPL/WNDR4300-V1.0.1.42_gpl_src.zip
wget ftp://downloads.netgear.com/files/GPL/WNDR4300-V1.0.1.30_gpl_src.zip
wget https://www.mikeburragejr.com/wp-content/uploads/2016/12/WNDR4300-V1.0.1.42b.patch
unzip WNDR4300-V1.0.1.42_gpl_src.zip
bzip2 -d WNDR4300-V1.0.1.42_gpl_src.tar.bz2
tar -xf WNDR4300-V1.0.1.42_gpl_src.tar
unzip -o WNDR4300-V1.0.1.30_gpl_src.zip
bzip2 -d toolchain.tar.gz.bz2
tar -zxvf toolchain.tar.gz -C wndr4300-GPL.git
cd wndr4300-GPL.git

# Apply my patch here.
git init
git commit -m "Initial commit."
git apply ../WNDR4300-V1.0.1.42b.patch

cp configs/defconfig-wndr4300 .config
GIT_HOME=`pwd`/git_home make V=99 PROJECT_MODELNAME=WNDR4300

The above will build the modified WNDR4300 firmware, with the following edits made by me to fix the vulnerabilities and get it to build on Fedora 20:

  • elf.cpp: In static member function ‘static Elf::file* Elf::file::open(const char*)’:
    elf.cpp:68:5: error: ‘::close’ has not been declared

    Edited elf.cpp in dl/mklibs_0.1.29.tar.gz to “#include <unistd.h>” at the top of the file.

  • quilt requires at least version 2.4 of GNU patch. You can download a
    current version of patch from ftp.gnu.org, or if you already have GNU patch
    then you can supply its path with the ‘–with-patch=’ option.

    Edited the configure file in dl/quilt_0.47.tar.gz, changing patch_version=$2 to patch_version=$3

  • Makefile:400: *** mixed implicit and normal rules. Stop.
    Makefile:1200: *** mixed implicit and normal rules. Stop.

    Edited Makefile in git_home/busybox.git, splitting the ‘config %config’ and ‘/ %/’ rules into 2 rules each.

  • Removed the git_home/net-cgi.git/usr/www/browser_hijack/BRS_02_genieHelp.html and git_home/net-cgi.git/usr/www/browser_hijack/BRS_03B_haveBackupFile_fileRestore.html file.
  • Disable the telnetEnable handler in package/telnetenable/files/RtDebug.sh (removing the /usr/sbin/telnetEnable line).
  • And removed the telnet daemon initialization via removing telnet related lines in configs/defconfig-wndr4300, telnet-related lines in package/base-files/files/etc/preinit, and startup scripts in package/dnibusybox/files/telnet and package/utelnetd/files/utelnetd.init

At that point, the modified firmware will be in bin/WNDR4300-V1.0.1.42.img, you can install it via the web admin interface and those 2 security vulnerabilities should be closed.

Or just grab WNDR4300-V1.0.1.42b.img (build by me), and install it.

At some point I’ll get around to some of the other annoyances with the router:

  • make the NTP servers configurable rather than being stuck with NETGEAR’s NTP servers (they’ve been unavailable several times recently)
  • fix the noisy logs with lots of false positives
  • disable proftpd, or figure out why it’s there
  • enable dropbear SSH access
  • retain the SSL cert across reboots

Leave a Reply

Your email address will not be published. Required fields are marked *

*

This site uses Akismet to reduce spam. Learn how your comment data is processed.