diff --git a/Lab4/.idea/.gitignore b/Lab4/.idea/.gitignore
new file mode 100644
index 0000000..13566b8
--- /dev/null
+++ b/Lab4/.idea/.gitignore
@@ -0,0 +1,8 @@
+# Default ignored files
+/shelf/
+/workspace.xml
+# Editor-based HTTP Client requests
+/httpRequests/
+# Datasource local storage ignored files
+/dataSources/
+/dataSources.local.xml
diff --git a/Lab4/.idea/Lab4.iml b/Lab4/.idea/Lab4.iml
new file mode 100644
index 0000000..f08604b
--- /dev/null
+++ b/Lab4/.idea/Lab4.iml
@@ -0,0 +1,2 @@
+
+
\ No newline at end of file
diff --git a/Lab4/.idea/codeStyles/codeStyleConfig.xml b/Lab4/.idea/codeStyles/codeStyleConfig.xml
new file mode 100644
index 0000000..a55e7a1
--- /dev/null
+++ b/Lab4/.idea/codeStyles/codeStyleConfig.xml
@@ -0,0 +1,5 @@
+
+
+
+
+
\ No newline at end of file
diff --git a/Lab4/.idea/misc.xml b/Lab4/.idea/misc.xml
new file mode 100644
index 0000000..79b3c94
--- /dev/null
+++ b/Lab4/.idea/misc.xml
@@ -0,0 +1,4 @@
+
+
+
+
\ No newline at end of file
diff --git a/Lab4/.idea/modules.xml b/Lab4/.idea/modules.xml
new file mode 100644
index 0000000..0c0d001
--- /dev/null
+++ b/Lab4/.idea/modules.xml
@@ -0,0 +1,8 @@
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Lab4/.idea/vcs.xml b/Lab4/.idea/vcs.xml
new file mode 100644
index 0000000..6c0b863
--- /dev/null
+++ b/Lab4/.idea/vcs.xml
@@ -0,0 +1,6 @@
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Lab4/CMakeLists.txt b/Lab4/CMakeLists.txt
new file mode 100644
index 0000000..030d41a
--- /dev/null
+++ b/Lab4/CMakeLists.txt
@@ -0,0 +1,6 @@
+cmake_minimum_required(VERSION 3.22)
+project(Lab4 C)
+
+set(CMAKE_C_STANDARD 99)
+
+add_executable(Lab4 Lab4.c)
diff --git a/Lab4/Lab4.c b/Lab4/Lab4.c
new file mode 100644
index 0000000..76328f4
--- /dev/null
+++ b/Lab4/Lab4.c
@@ -0,0 +1,100 @@
+/*
+ * Question 2: You see the number 1 most of the time. It is sometimes different because there are periods of time when the threads are reading/writing to the same place, but with the number of increments being 100, it is not likely that the threads will be reading/writing at the same time. In the CPU what happens is that a value is loaded into a register, while another thread completes a task, and then the value is written back to the memory. This leads to missing increments/decrements.
+ *
+ * Question 4: You see the number 1 often. Since the number of increments is 1000, the chance has increased for threads to be reading/writing at the same time. This leads to more missing increments/decrements.
+ *
+ * Question 6: You see the number 1 almost never. The number of loops at this point almost guarantees that the threads will be reading/writing at the same time, and the counter missing increments/decrements.
+ *
+ * Question 8: The number 1 is the only thing displayed. This is because the mutex lock ensures that the threads will not be reading/writing at the same time, and the counter will not miss increments/decrements. When another thread tried to lock the mutex, it waits for it to first become unlocked, ensuring proper thread synchronization.
+ */
+
+
+#include
+#include
+#include
+#include
+#include
+
+#define RANDOM_WITHIN_RANGE(a, b, seed) (rand_r(&seed)%b+a)
+
+int gv = 1;
+pthread_mutex_t mutex;
+sem_t sem;
+
+#define loop 10000
+
+void *inc() {
+ for (int i = 0; i < loop; i++) {
+ pthread_mutex_lock(&mutex);
+ gv++;
+ pthread_mutex_unlock(&mutex);
+ }
+}
+
+void *dec() {
+ for (int i = 0; i < loop; i++) {
+ pthread_mutex_lock(&mutex);
+ gv--;
+ pthread_mutex_unlock(&mutex);
+ }
+}
+
+void *minus() {
+ int i = 0;
+ for (i = 0; i < 10; i++) {
+ printf("-");
+ sem_wait(&sem);
+ }
+ return NULL;
+}
+
+void *plus(void *argg) {
+ unsigned int seed = *((unsigned int *) argg);
+ int interval = RANDOM_WITHIN_RANGE(100000, 500000, seed);
+ int i = 0;
+
+ for (i = 0; i < 10; i++) {
+ printf("+");
+ //usleep(interval);
+ sem_post(&sem);
+ }
+ return NULL;
+}
+
+int main(int argc, char **argv) {
+ setvbuf(stdout, NULL, _IONBF, 0);
+ int i = 0;
+
+ // Init Mutex
+ pthread_mutex_init(&mutex, NULL);
+ // Create thread pool and run threads
+ pthread_t thread[2];
+ pthread_create(&thread[i], NULL, &inc, NULL);
+ pthread_create(&thread[i + 1], NULL, &dec, NULL);
+ // Wait for threads to finish
+ pthread_join(thread[i], NULL);
+ pthread_join(thread[i + 1], NULL);
+ // Destroy Mutex
+ pthread_mutex_destroy(&mutex);
+ // Print final value
+ printf("%d\n", gv);
+
+ // Init Semaphore
+ sem_init(&sem, 0, 0);
+ for (i = 0; i < 1; i++) {
+ unsigned int *t = (unsigned int *) malloc(sizeof(unsigned int));
+ *t = rand();
+
+ pthread_create(&(thread[i]), NULL, &plus, (void *) t);
+ pthread_create(&(thread[i + 1]), NULL, &minus, NULL);
+
+ pthread_join(thread[i], NULL);
+ pthread_join(thread[i + 1], NULL);
+ }
+ sem_destroy(&sem);
+
+ return 0;
+}
+//TODO: Delete this comment
+//Semaphore doesn't work because it increments the semaphore all at once before the other thread even gets the chance to print
+//Just as an example to fix it you would need two semaphores so you can signal back and forth between the two threads
\ No newline at end of file
diff --git a/Lab4/documentation/Lab4.pdf b/Lab4/documentation/Lab4.pdf
new file mode 100644
index 0000000..ee9251a
Binary files /dev/null and b/Lab4/documentation/Lab4.pdf differ
diff --git a/Lab4/run.sh b/Lab4/run.sh
new file mode 100644
index 0000000..8b96d3d
--- /dev/null
+++ b/Lab4/run.sh
@@ -0,0 +1,8 @@
+#!/usr/bin/env bash
+while :
+ do
+ output=$(./build/Lab4)
+ if [ "$output" != "1" ]; then
+ echo "$output"
+ fi
+ done