diff --git a/userprog/argument_parsing.h b/userprog/argument_parsing.h
index 37b47e8003c0e7bdbc9cd3cabcb1eca421e8aa82..b84be707d1c4adb0e17dfeb8f92c75ce4908e8e7 100644
--- a/userprog/argument_parsing.h
+++ b/userprog/argument_parsing.h
@@ -1,14 +1,26 @@
+/*
+ * argument_parsing.h --prototypes functions required for parsing arguments from
+ * command line and placing these into the program stack structure.
+ *
+ * Authored by Joshua Saxby
+ */
 #ifndef USERPROG_ARGUMENT_PARSING_H
 #define USERPROG_ARGUMENT_PARSING_H
 
+
+// some macros for argument length and count limits
+// TODO: decide how many arguments we want --is 255 the standard number?
+#define USERPROG_ARGV_COUNT 255
+// TODO: clarify what a sensible value for this is
+#define USERPROG_RAW_ARGV_LENGTH 255
+
 /*
  * Given a string containing the command invoking the program `command_line`
- * and a pointer to an array of C strings (pointer to `char* argv[]`), parse
- * `command_line` into individual arguments, populate `argv` with these and
- * return the number of arguments that were parsed (this is the value that can
- * be used for `argc`).
+ * and an array of C strings (pointer to `char* argv[]`), parse `command_line`
+ * into individual arguments, populate `argv` with these and return the number
+ * of arguments that were parsed (this is the value that can be used for `argc`).
  */
-int parse_arguments(const char* command_line, char***argv);
+int parse_arguments(const char* command_line, char**argv);
 
 /*
  * Given stack pointer `esp`, argument count `argc` and arguments array `argv`,
diff --git a/userprog/parse_arguments.c b/userprog/parse_arguments.c
index aeaefd0778156808a54f8c2b1da7b1197886efbc..9de6f294fa5d77fc3319b6a36cb7c52458ed1241 100644
--- a/userprog/parse_arguments.c
+++ b/userprog/parse_arguments.c
@@ -1,6 +1,29 @@
+/*
+ * parse_arguments.c --implements function for parsing a command-line string
+ * into the program arguments contained within it.
+ *
+ * Authored by Joshua Saxby
+ */
+#include <stddef.h>
+#include <string.h>
+
 #include "userprog/argument_parsing.h"
 
 
-int parse_arguments(const char* command_line, char***argv) {
-    #warning "Implement me"
+int parse_arguments(const char* command_line, char**argv) {
+    int argc = 0;
+    // the state pointer required by strtok_r() for use between calls
+    char* state_pointer;
+    // first call to strtok_r() is the only one where string to parse is passed
+    argv[0] = strtok_r(command_line, " ", &state_pointer);
+    argc++;
+    // now, parse token-by-token for any additional arguments
+    char* token = strtok_r(NULL, " ", &state_pointer);
+    // continue while still tokens to read and maximum arg count is not reached
+    while (token != NULL && argc < USERPROG_ARGV_COUNT) {
+        argv[argc] = token;
+        argc++;
+        token = strtok_r(NULL, " ", &state_pointer);
+    }
+    return argc;
 }
diff --git a/userprog/process.c b/userprog/process.c
index e5b66aa9108910c254ec627497800cadc2c3b0bb..98ff0aaff1c93c0851eefa08c7a947534314f5d0 100644
--- a/userprog/process.c
+++ b/userprog/process.c
@@ -5,6 +5,7 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include "userprog/argument_parsing.h"
 #include "userprog/gdt.h"
 #include "userprog/pagedir.h"
 #include "userprog/tss.h"
@@ -20,7 +21,6 @@
 
 static thread_func start_process NO_RETURN;
 static bool load (const char *cmdline, void (**eip) (void), void **initial_stack_pointer);
-
 /* Starts a new thread running a user program loaded by parsing
    COMMAND. The new thread may be scheduled (and may even exit)
    before process_execute() returns.  Returns the new process's
@@ -29,24 +29,22 @@ tid_t
 process_execute (const char *command)
 {
   char *command_copy;
-  tid_t tid;
-
   /* Make a copy of COMMAND.
      Otherwise there's a race between the caller and load(). */
   command_copy = palloc_get_page (0);
   if (command_copy == NULL)
     return TID_ERROR;
   strlcpy (command_copy, command, PGSIZE);
+  // we need to extract out the filename from the command string
+  char* file_name;
+  char* save_ptr; // this is the save pointer expected by strtok_r()
+  // file name is the first part of the command-line (space-delimited)
+  file_name = strtok_r(command, " ", &save_ptr);
+  tid_t tid;
+
 
   /* Create a new thread to execute COMMAND. */
-  /*
-   * FIXME: right now, COMMAND is assumed to be just the filename on its own
-   *
-   * If this is not the case (if the user passed a program name with arguments),
-   * then loading will fail.
-   * NOTE: remove this comment block when argument parsing is implemented.
-   */
-  tid = thread_create (command, PRI_DEFAULT, start_process, command_copy);
+  tid = thread_create (file_name, PRI_DEFAULT, start_process, command_copy);
 
   if (tid == TID_ERROR)
     palloc_free_page (command_copy);
@@ -218,7 +216,7 @@ static bool load_segment (struct file *file, off_t ofs, uint8_t *upage,
                           uint32_t read_bytes, uint32_t zero_bytes,
                           bool writable);
 
-/* Loads an ELF executable from FILE_NAME into the current thread.
+/* Loads an ELF executable from COMMAND into the current thread.
    Stores the executable's entry point into *EIP
    and its initial stack pointer into *initial_stack_pointer.
    Returns true if successful, false otherwise. */
@@ -232,6 +230,14 @@ load (const char *cmdline, void (**eip) (void), void **initial_stack_pointer)
   bool success = false;
   int i;
 
+  // extract arguments (including file name)
+  char* argv[USERPROG_ARGV_COUNT];
+  // copy the command string so we have a separate copy to manipulate
+  char command_copy[USERPROG_RAW_ARGV_LENGTH];
+  strlcpy(command_copy, cmdline, USERPROG_RAW_ARGV_LENGTH);
+  int argc = parse_arguments(command_copy, argv);
+  char* file_name = argv[0]; // file name is always argument 0
+
   /* Allocate and activate page directory. */
   t->pagedir = pagedir_create ();
   if (t->pagedir == NULL) 
@@ -239,7 +245,7 @@ load (const char *cmdline, void (**eip) (void), void **initial_stack_pointer)
   process_activate ();
 
   /* Open executable file. */
-  file = filesys_open (cmdline);
+  file = filesys_open (file_name);
 
   if (file == NULL) 
     {
@@ -320,7 +326,7 @@ load (const char *cmdline, void (**eip) (void), void **initial_stack_pointer)
     }
 
   /* Set up stack. */
-  if (!setup_stack (initial_stack_pointer))
+  if (!setup_stack (initial_stack_pointer, argv, argc))
     goto done;
 
   /* Start address. */
@@ -456,6 +462,7 @@ setup_stack (void **initial_stack_pointer, char **argv, int argc)
       success = install_page (((uint8_t *) PHYS_BASE) - PGSIZE, kpage, true);
       if (success) {
         *initial_stack_pointer = PHYS_BASE - 12;
+        populate_stack(initial_stack_pointer, argc, argv);
       } else
         palloc_free_page (kpage);
     }