do some other shit to 1 idk
This commit is contained in:
+39
-31
@@ -10,8 +10,10 @@
|
|||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <random>
|
#include <random>
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
|
#include <cmath>
|
||||||
|
|
||||||
constexpr int NIL = -1;
|
constexpr int NIL = -1;
|
||||||
|
constexpr int MAX_PROCS = 1024; // Safety buffer for return values
|
||||||
|
|
||||||
struct Node {
|
struct Node {
|
||||||
int value;
|
int value;
|
||||||
@@ -20,6 +22,7 @@ struct Node {
|
|||||||
|
|
||||||
struct SharedData {
|
struct SharedData {
|
||||||
int head;
|
int head;
|
||||||
|
int results[MAX_PROCS]; // Section for returning results in SHM
|
||||||
Node nodes[1];
|
Node nodes[1];
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -113,82 +116,87 @@ int local_list_sort(Node* pool, int head) {
|
|||||||
return merge_lists(pool, left, right);
|
return merge_lists(pool, left, right);
|
||||||
}
|
}
|
||||||
|
|
||||||
int parallel_list_sort(Node* pool, int head, int depth, int max_depth) {
|
// proc_idx helps each process find its unique slot in data->results
|
||||||
|
int parallel_list_sort(SharedData* data, int head, int depth, int max_depth, int proc_idx) {
|
||||||
log_start(head, depth);
|
log_start(head, depth);
|
||||||
|
|
||||||
if (head == NIL || pool[head].next == NIL) {
|
if (head == NIL || data->nodes[head].next == NIL) {
|
||||||
log_end(head, depth);
|
log_end(head, depth);
|
||||||
return head;
|
return head;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (depth >= max_depth) {
|
if (depth >= max_depth) {
|
||||||
int result = local_list_sort(pool, head);
|
int result = local_list_sort(data->nodes, head);
|
||||||
log_end(result, depth);
|
log_end(result, depth);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
int left_part, right_part;
|
int left_part, right_part;
|
||||||
split_list(pool, head, left_part, right_part);
|
split_list(data->nodes, head, left_part, right_part);
|
||||||
|
|
||||||
int pipe_l[2], pipe_r[2];
|
// Calculate unique IDs for children in the results array
|
||||||
pipe(pipe_l);
|
int left_child_idx = 2 * proc_idx + 1;
|
||||||
pipe(pipe_r);
|
int right_child_idx = 2 * proc_idx + 2;
|
||||||
|
|
||||||
// Левый потомок
|
|
||||||
pid_t pid_l = fork();
|
pid_t pid_l = fork();
|
||||||
if (pid_l == 0) {
|
if (pid_l == 0) {
|
||||||
close(pipe_l[0]); close(pipe_r[0]); close(pipe_r[1]);
|
int res = parallel_list_sort(data, left_part, depth + 1, max_depth, left_child_idx);
|
||||||
int res = parallel_list_sort(pool, left_part, depth + 1, max_depth);
|
data->results[left_child_idx] = res; // Return result in SHM
|
||||||
write(pipe_l[1], &res, sizeof(int));
|
|
||||||
close(pipe_l[1]);
|
|
||||||
_exit(0);
|
_exit(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Правый потомок
|
|
||||||
pid_t pid_r = fork();
|
pid_t pid_r = fork();
|
||||||
if (pid_r == 0) {
|
if (pid_r == 0) {
|
||||||
close(pipe_r[0]); close(pipe_l[0]); close(pipe_l[1]);
|
int res = parallel_list_sort(data, right_part, depth + 1, max_depth, right_child_idx);
|
||||||
int res = parallel_list_sort(pool, right_part, depth + 1, max_depth);
|
data->results[right_child_idx] = res; // Return result in SHM
|
||||||
write(pipe_r[1], &res, sizeof(int));
|
|
||||||
close(pipe_r[1]);
|
|
||||||
_exit(0);
|
_exit(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Родитель ждет обоих
|
// Synchronize: Parent waits for both children to finish writing to SHM
|
||||||
int sorted_l, sorted_r;
|
|
||||||
close(pipe_l[1]); close(pipe_r[1]);
|
|
||||||
|
|
||||||
waitpid(pid_l, nullptr, 0);
|
waitpid(pid_l, nullptr, 0);
|
||||||
read(pipe_l[0], &sorted_l, sizeof(int));
|
|
||||||
|
|
||||||
waitpid(pid_r, nullptr, 0);
|
waitpid(pid_r, nullptr, 0);
|
||||||
read(pipe_r[0], &sorted_r, sizeof(int));
|
|
||||||
|
|
||||||
close(pipe_l[0]); close(pipe_r[0]);
|
// Read results directly from Shared Memory
|
||||||
|
int sorted_l = data->results[left_child_idx];
|
||||||
|
int sorted_r = data->results[right_child_idx];
|
||||||
|
|
||||||
int final_head = merge_lists(pool, sorted_l, sorted_r);
|
int final_head = merge_lists(data->nodes, sorted_l, sorted_r);
|
||||||
log_end(final_head, depth);
|
log_end(final_head, depth);
|
||||||
return final_head;
|
return final_head;
|
||||||
}
|
}
|
||||||
|
|
||||||
int main(int argc, char* argv[]) {
|
int main(int argc, char* argv[]) { //main(data count, max recursion level)
|
||||||
int n = 1000;
|
int n = 10000;
|
||||||
int max_depth = 3;
|
int max_depth = 3;
|
||||||
if (argc > 1) n = std::atoi(argv[1]);
|
if (argc > 1) n = std::atoi(argv[1]);
|
||||||
if (argc > 2) max_depth = std::atoi(argv[2]);
|
if (argc > 2) max_depth = std::atoi(argv[2]);
|
||||||
|
|
||||||
size_t shm_size = sizeof(int) + sizeof(Node) * n;
|
size_t shm_size = sizeof(SharedData) + sizeof(Node) * (n - 1);
|
||||||
int shmid = shmget(IPC_PRIVATE, shm_size, IPC_CREAT | 0666);
|
int shmid = shmget(IPC_PRIVATE, shm_size, IPC_CREAT | 0666);
|
||||||
SharedData* data = (SharedData*)shmat(shmid, nullptr, 0);
|
SharedData* data = (SharedData*)shmat(shmid, nullptr, 0);
|
||||||
|
|
||||||
|
// Initialize return area
|
||||||
|
for(int i = 0; i < MAX_PROCS; ++i) data->results[i] = NIL;
|
||||||
|
|
||||||
|
data->head = 0;
|
||||||
std::mt19937 rng(time(0));
|
std::mt19937 rng(time(0));
|
||||||
std::uniform_int_distribution<int> dist(0, 9999);
|
std::uniform_int_distribution<int> dist(0, 999);
|
||||||
|
|
||||||
for (int i = 0; i < n; ++i) {
|
for (int i = 0; i < n; ++i) {
|
||||||
data->nodes[i].value = dist(rng);
|
data->nodes[i].value = dist(rng);
|
||||||
data->nodes[i].next = (i == n - 1) ? NIL : i + 1;
|
data->nodes[i].next = (i == n - 1) ? NIL : i + 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
data->head = parallel_list_sort(data->nodes, data->head, 0, max_depth);
|
// Start with proc_idx 0 (the root)
|
||||||
|
data->head = parallel_list_sort(data, data->head, 0, max_depth, 0);
|
||||||
|
|
||||||
|
std::cout << "\nSorted list (first 20 elements): ";
|
||||||
|
int curr = data->head;
|
||||||
|
for(int i = 0; i < 20 && curr != NIL; ++i) {
|
||||||
|
std::cout << data->nodes[curr].value << " ";
|
||||||
|
curr = data->nodes[curr].next;
|
||||||
|
}
|
||||||
|
std::cout << std::endl;
|
||||||
|
|
||||||
shmdt(data);
|
shmdt(data);
|
||||||
shmctl(shmid, IPC_RMID, nullptr);
|
shmctl(shmid, IPC_RMID, nullptr);
|
||||||
|
|||||||
Reference in New Issue
Block a user