~stick/challenges

b86baa7b4eec735548159e74ebeb4f042ac78322 — Stick a month ago 73ff92f master
stuff from cyberstakes 2020
A all_army_cyber_stakes/2020/BinEx101 => all_army_cyber_stakes/2020/BinEx101 +0 -0

A all_army_cyber_stakes/2020/BinEx101.c => all_army_cyber_stakes/2020/BinEx101.c +187 -0
@@ 0,0 1,187 @@
#include <stdio.h>
#include <stdlib.h>

#define FLAG_SIZE 64

/* Function prototype for `initialize`
 *     Allows `main` to call it without the definition.  Usually you see these
 * in a separate header file.  It also tells you that it "returns" a "char *"
 * (left side of the function name) and takes "void" (a synonym for nothing) as
 * the parameters (what's inside the parenthesis).
 */
char *initialize(void);





/* A "struct" definition.
 *     This creates a reusable "type" that packages other types (like pointers,
 * integers, floats, and even other structs) into a well-defined representation
 * in memory.  While there are lots of rules to ensure fields are correctly
 * "aligned" in memory, the important concept here is that fields earlier in
 * the definition of the struct are "lower" in memory.
 */
struct dynamic_strings {
  char *flag;
  char *numbers[10];
};
/* EXPLANATION:
 *
 * "char *flag;"
 * `flag` is a "pointer" to a "char" - a signed, single byte numbers which are
 * commonly used to represent text "strings".
 *
 * "char *numbers[10];"
 * `numbers` is an "array" of "char pointers".  An array just means that the
 * type on the left "char *" is repeated a number of times (10 in this case).
 * This is an example of a "static" sized array which means it will always
 * have 10 slots in it.  We can access the slots through the notation
 *     array[index]
 * where "array" is replaced by the variable name (numbers in this case) and
 * "index" is replaced with the position you want to access (starting with 0).
 * In other words, numbers[0] is the first element, numbers[1] is the second,
 * and so on.
 *
 * Under the hood, the compiler & computer convert this into arithmetic
 * composed of applying an offset to the "base" (first element of the array).
 * Going back to "array[index]", the compiler essentially converts this into
 * accessing the memory at (where array_type is the "type" of each element):
 *     array + sizeof(array_type) * index
 * A consequence of this construction is that the compiler and computer
 * allow code like "array[-1]" which will access an "element" immediately
 * before the first.  Accesses like this are frequrently unintentional and
 * can often allow hackers to exploit the program for their own purposes.
 *
 * For this specific instance,
 *     numbers[-1] == flag
 * which should be an early indication of where we should focus our efforts
 * for exploiting this program.
 */





/* This is the `main` function.  Every C program will have one (and most
 * languages define some kind of equivalent).  This is generally, but not
 * always, a good place to start when analyzing a program since it is the
 * logical start point for the code a programmer wrote.
 */
void main(void) {
  /* The next two lines define two "variables" that we use to store and
   * reference values later.  In C, an "int" is a 32-bit, signed integer.
   */
  int first;
  int second;


  /* This section of code creates a new "instance" of our struct we defined
   * above.  It also "initializes" it by setting "flag" (the first field) to
   * the return value of `initialize` and the "numbers" array to point to the
   * strings defined in line.  You should notice that there are exactly 10
   * strings given inside the curly braces which matches the size of "numbers".
   */
  struct dynamic_strings s = {
    initialize(),
    {
      "zero",
      "one",
      "two",
      "three",
      "four",
      "five",
      "six",
      "seven",
      "eight",
      "nine"
    }
  };


  /* This section of code prompts the user for input and then reads it in as
   * an integer.  If the input was either not an integer or negative, it prints
   * an appropriate error code and exits.
   */
  puts("Give me a number:\r");         /* Prompt for input */
  if (!scanf("%d", &first)) {          /* Read input and store in `first` */
    /* `scanf` return a non-zero number (C for "true") on success, this means
     * `!scanf(...)` can be read as "scanf was not successful" since the '!'
     * symbol means a logical negation (i.e. the opposite "truth value" of
     * what it was).  That means we only execute the next two lines if the
     * user did not enter a valid number (empty or had non-numeric characters).
     */
    puts("Error: unrecognized input\r");
    exit(1); /* Exiting with a number other than 0 generally indicates a program
              * error occurred.
              */
  }
  if (first <= 0) { /* Checks if the inputted number is negative */
    puts("Error: input must be positive\r");
    exit(1);
  }

  /* Repeat the process for "second" */
  puts("Give me another number:\r");
  if (!scanf("%d", &second)) {
    puts("Error: unrecognized input\r");
    exit(1);
  }
  if (second <= 0) {
    puts("Error: input must be positive\r");
    exit(1);
  }


  /*************************************************************
   ********************** VULNERABLE CODE **********************
   *************************************************************/
  int tmp = first * second;
  /* In some languages (e.g. Python 3) there are no issues with the line above
   * and it will always match the intuitive meaning: `tmp` equals the product
   * of the two integers that were passed in and is therefore positive.
   *
   * However, this is not how C (or most languages with fixed-width integers)
   * works.  Instead the calculation can "overflow" the highest expressible
   * integer and wrap around to the lowest expressible integer and keep going.
   * In other words, it is entirely possible to get a negative number for
   * `tmp` by multiplying two numbers that are less than INT_MAX (2147483647).
   *
   * In the line below, we create the vulnerability by using `tmp` to access
   * the "numbers" array in our struct.  In C the modulo operator (%) (also
   * known as "remainder"), has the same sign as the left-hand side.  This
   * means if `tmp` is negative, we will end up accessing memory that is
   * outside of the array.
   *
   * How can we leverage this to print the flag?
   */
  printf("%d * %d = %d which ends in a '%s'\r\n",
         first, second, tmp, s.numbers[tmp % 10]);
}





/* For the purposes of this problem (and many of the other CTF problems), this
 * is basically boilerplate code.  If you're interested in better understanding
 * what this code is doing, you can read more about each of the function calls
 * by typing `man 3 <function>` into a UNIX terminal (such as our shell server).
 * This will give you the function information for the calls.
 */
char *initialize(void) {
  setvbuf(stdin, NULL, _IONBF, 0);
  setvbuf(stdout, NULL, _IONBF, 0);
  setvbuf(stderr, NULL, _IONBF, 0);

  char *flag = malloc(FLAG_SIZE);
  FILE *file;
  file = fopen("flag.txt", "r");
  if (file == NULL) {
    puts("Error: could not open the flag\r");
    exit(0);
  }
  fgets(flag, FLAG_SIZE, file);
  fclose(file);
  return flag;
}

A all_army_cyber_stakes/2020/RE101 => all_army_cyber_stakes/2020/RE101 +0 -0

A all_army_cyber_stakes/2020/document.encrypted => all_army_cyber_stakes/2020/document.encrypted +15 -0
@@ 0,0 1,15 @@
36a36e90d5a591146e2c02fae3758fa579df0be600f685fa81fe8311f1424c370a7b98058f8cbddf47bcc93b700a9801967639b81dc2f4b61a5da08934abf4f0
58c15ff1fd8db258441823dba414a69b52f14fd92182adb4a1d2b92cd4176e133809b53eaf8c93f5339f8c585f22bc28b11378d975a08bd90970cfb30f97ced7
42c143ffe78fb158461427d2a412a5875c9027cc3093a0b4acd9b131d417771e2d1ad93fa5f88cfc478de55e4531af44bb1e19ca75b986b86c75c8a47be5a1a3
42c14ff5ff9ebc58471433c0d61abeeb49f92ad13697ccd0a0dba139b57368172d1ad92daff888903497e9494522ce26aa170ed719b18fc86177a0cb7be5a1a3
42c149e2f29cb25852122ec6d614ca8852f13dcf2d93ccdcaac3b034b57062173f7bb83bbae48890239be04f5643ba25b61117b878bc93d06816c4ae1791c0a3
42c158f9f698af39211324c0c119ca8c55fc29a33097a2d3aab7b237d9710d12371fb036caef81f13592e55e3739ab30b97602dd6db1e3dd6a7ecfcb7be5a1a3
42c148f8f298b131447b28dcc507a6825f902bc62882adb4a7c5b42eda176c172913b857b9e58ce2359f8c5a5b33a625d81017c06da28ccc0974d2aa0d8aa1a3
42c143ffe78fb15848152fddc575ab874af82ea33097a2d3aab7b03bdd780d0f3815be38caf888fe20918c5e542ba144b1181cd178d086db6179a0cb7be5a1a3
42c15ff1fd8db258441823dba41ca48f53f14fc42b9aaab4a0d4bd37b5757f1a2f14d936a6fc81f1478aed55502cce30b9181fd719b580d06616c8a40f80cda3
42c142fef783bc5849143fd1c875ae8e56e42ea3379fa9c6b7d6d53bdd767f17301ed930a5e08f90239be04f5643a82ba0020ad76dd081ca6860cfcb7be5a1a3
42c149e2f29cb25849143fd1c875a9835be223ca21f6a8d1a9c3b458d07465145908b032b8fe88902496ed495b2aab44ab1f1dca6bb1e3da7b77d6a47be5a1a3
42c12b9093eadd58217b4bb4a475caeb3a904fa344f6ccb4c5b7d558b5170d7b597bd957ca8ce99047fe8c3b3743ce44d87678b819d0e3b80916a0cb7be5a1a3
42c14dc5c1be951d733604e6e179cabf72d54fc52897abb48ce4cf58b5170d7b597bd957ca8ce99047fe8c3b3743ce44d87678b819d0e3b80916a0cb7be5a1a3
42c101f1f083861e346d5aa2b5658efc7fd55ce152e1d9a4d0f6c24af3514b6c40638457ca8ce99047fe8c3b3743ce44d87678b819d0e3b80916a0cb7be5a1a3
42eb01

A all_army_cyber_stakes/2020/flag => all_army_cyber_stakes/2020/flag +1 -0
@@ 0,0 1,1 @@
ACI{g3tt!ng_m0r3_R4nd0M_45df147a}
\ No newline at end of file

A all_army_cyber_stakes/2020/flag.enc => all_army_cyber_stakes/2020/flag.enc +1 -0
@@ 0,0 1,1 @@
17049023077889510260204396207184665258344085011807070220020536481847552482277066961336377469039308145383355452260087653195886505757836917258354810528945868970696334631473598799034921183145491181376234988499964955903401485360911350813348919297429369498534842626287775480312270341128898460764804807214999914042028957245781616720506700448572915572787985572510661747455475602730791868916847192195119959230446274599563370873476155933682798499522758074728424080527146821745717447570777424276681712058208568774387764187301563390843386692020857646007853761886323627794612713069218139646677305318191428305263694365029026661638
\ No newline at end of file

A all_army_cyber_stakes/2020/flag.png => all_army_cyber_stakes/2020/flag.png +0 -0

A all_army_cyber_stakes/2020/flag.txt => all_army_cyber_stakes/2020/flag.txt +1 -0
@@ 0,0 1,1 @@
ACI{Something_witty_646b0c84}
\ No newline at end of file

A all_army_cyber_stakes/2020/floppy.img => all_army_cyber_stakes/2020/floppy.img +0 -0

A all_army_cyber_stakes/2020/lockbox => all_army_cyber_stakes/2020/lockbox +0 -0

A all_army_cyber_stakes/2020/not_so_meta.jpg => all_army_cyber_stakes/2020/not_so_meta.jpg +0 -0

A all_army_cyber_stakes/2020/params.txt => all_army_cyber_stakes/2020/params.txt +3 -0
@@ 0,0 1,3 @@
p = 237749804922280625536682309685409336043453398811176073274884763712898570123603466963723116791720932452234065213520743172716385740340487427123095074536317694600298665468597616303314249385693363215053056844977253069039661253880116845026155205965865895100623627364736539283402561320733902401683578425719402004499
q = 345513032878824680216407101297437782364589961569407696102527137527577263750045643543979399075714436073238866093607645134205379572809538474494136659110222523938224662781965327948507231240376086254472564421988975316092976983573364457290943004665956738947910342595588904010377629977428854646844786015090074409559
e = 103979276676151675244175035873238481327150395814487520977518943224974781688167
\ No newline at end of file