Program received signal SIGSEGV, Segmentation fault. 0x00005555555554c6 in pop () очередь с приоритетом Си
Делаю задание по реализации очереди с приоритетом на си, с операциями вставки, извлечения первого элемента, элемента с заданным приоритетом и с приоритетом не ниже заданного.Приоритет задаётся числом от 1 до 255. С добавлением всё в порядке, но корректно извлекаются только первые 2 элемента, 3 извлекается, но затем при повторной попытке извлечения либо вывода содержимого происходит segmentation fault. Если при извлечении память не освобождать работает всё корректно. В чём ошибка?
queue.c
#include <stdio.h>
#include <stdlib.h>
#include "queue.h"
Queue* enqueue( Queue *head, int data, unsigned priority)
{
Queue* buf = (Queue*)malloc(sizeof(Queue));
Queue* tmp;
buf->data = data;
buf->priority = priority;
buf->next = NULL;
if(head == NULL)
{
buf->rear = buf;
buf->front = buf;
return buf;
}
tmp = head->front;
if(head->front->priority > buf->priority)
{
buf->next = head->front;
head->front = buf;
return head;
}
while(tmp->next != NULL)
{
if(buf->priority < tmp->next->priority)
{
buf->next = tmp->next;
tmp->next = buf;
return head;
}
tmp = tmp->next;
}
head->rear = head->rear->next = buf;
return head;
}
int pop(Queue *head)
{
Queue *tmp;
int data;
if(head == NULL)
{
printf("Queue empty!");
return 0;
}
tmp = head->front;
data = tmp->data;
head->front = head->front->next;
free(tmp);
return data;
}
int pop_priority(Queue *head, unsigned priority)
{
Queue *tmp;
Queue *buf;
int data;
if(head == NULL)
{
printf("Queue empty!");
return 0;
}
tmp = head->front;
if(tmp->priority == priority)
{
return pop(head);
//head->front = head->front->next;
}
while(tmp->next != NULL)
{
if(tmp->priority == priority)
{
data = tmp->next->data;
buf = tmp;
tmp = tmp->next;
//data = buf->data;
free(buf);
return data;
}
tmp = tmp->next;
}
if(tmp->next == NULL)
{
printf("Wrong priority");
return 0;
}
return 0;
}
int pop_under_priority(Queue *head, unsigned priority)
{
//Queue *tmp;
//int data;
if(head == NULL)
{
printf("Queue empty!");
return 0;
}
printf("Priority: %d\n", head->front->priority);
if(head->front->priority <= priority)
return pop(head);
else
printf("Wrong priority");
return 0;
}
void print_queue(Queue *head)
{
Queue* tmp = head->front;
if (NULL == head)
{
printf("List empty!\n");
return;
}
do
{
printf("%d\n", tmp->data);
tmp = tmp->next;
} while (tmp != NULL);
printf("\n");
}
queue.h
typedef struct Queue
{
unsigned priority;
int data;
struct Queue *front;
struct Queue *rear;
struct Queue *next;
}Queue;
Queue* enqueue( Queue *head, int x, unsigned priority);
int pop(Queue *front);
int pop_priority(Queue *head, unsigned priority);
int pop_under_priority(Queue *head, unsigned priority);
void print_queue(Queue *head);
main.c
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "queue.h"
int main()
{
Queue *head = NULL;
head = enqueue(head, 100, 2);
head = enqueue(head, 8, 4);
head = enqueue(head, 4, 3);
head = enqueue(head, 3, 2);
head = enqueue(head, 6, 1);
head = enqueue(head, 17, 1);
head = enqueue(head, 13, 6);
head = enqueue(head, 55, 4);
head = enqueue(head, 90, 8);
head = enqueue(head, 102, 10);
print_queue(head);
printf("\n%d\n", pop(head));
printf("\n%d\n\n", pop(head));
print_queue(head);
printf("\n%d\n\n", pop(head));
printf("\n%d\n\n", pop(head));
}