Implementation of annular Message Queue

Source: Internet
Author: User

Struct messagequeue
{
Int * m_parray;

// Message Queue Length
Int m_ilength;

// Read subscript of Message Queue
Int m_iread;

// Write subscript of Message Queue
Int m_iwrite;

// Mutex lock for multiple write operations
Pthread_mutex_t m_mutex;

// Condition variable of the Message Queue
Pthread_cond_t m_cond;
};

Messagequeue * ip_create_messagequeue (INT length)
{
Messagequeue * pmessagequeue = (messagequeue *) malloc (sizeof (messagequeue ));

If (null = pmessagequeue)
{
# Ifdef _ log
Printf ("% s: % d get memory is null", _ file __, _ line __);
# Else
Writelog (errlog, "% s: % d get memory is null", _ file __, _ line __);
# Endif
 
Return NULL;
}
Else
{
// Add a length
Length ++;
 
Pmessagequeue-> m_parray = (int *) malloc (sizeof (INT) * length );

If (null = pmessagequeue-> m_parray)
{
# Ifdef _ log
Printf ("% s: % d get memory is null", _ file __, _ line __);
# Else
Writelog (errlog, "% s: % d get memory is null", _ file __, _ line __);
# Endif

Free (pmessagequeue );

Return NULL;
}
Else
{
Memset (pmessagequeue-> m_parray, 0, length * sizeof (INT ));

Pmessagequeue-> m_ilength = length;
Pmessagequeue-> m_iread = pmessagequeue-> m_iwrite = 0;

// Initialize the mutex lock
Pthread_mutex_init (& (pmessagequeue-> m_mutex), null );

Pthread_cond_init (& (pmessagequeue-> m_cond), null );

Return pmessagequeue;
}
}
}

// Add one
Bool ip_in_messagequeue (messagequeue * pmessagequeue, int value)
{
Assert (null! = Pmessagequeue );
 
Int saveread = pmessagequeue-> m_iread;

// Write the subscript before reading the subscript
If (pmessagequeue-> m_iwrite> = saveread)
{
// When the subscripts are full before the subscripts are read, only the subscripts are in the same place.
// Or write the subscript at the end, and read the subscript before one
// The message queue is full.
If (pmessagequeue-> m_iwrite-pmessagequeue-> m_iread) = pmessagequeue-> m_ilength-2)
{
Return false;
}
 

/* If (pmessagequeue-> m_iwrite + 1 = pmessagequeue-> m_ilength-1)
& (Pmessagequeue-> m_iread = 0 ))
{
Return false;
}

If (pmessagequeue-> m_iwrite = pmessagequeue-> m_ilength-1)
& (Pmessagequeue-> m_iread = 1 ))
{
Return false;
}*/
}
// Write the subscript after reading the subscript
Else
{
// The interval between writing subscripts and reading subscripts is 1, indicating that the queue is full.
If (saveread-pmessagequeue-> m_iwrite = 1)
{
Return false;
}
}

// Write the message
(Pmessagequeue-> m_parray) [pmessagequeue-> m_iwrite] = value;

// It has been written to the end of the array
If (pmessagequeue-> m_iwrite = pmessagequeue-> m_ilength-1)
{
Pmessagequeue-> m_iwrite = 0;
}
Else
{
// Write the subscript to forward the first digit
++ (Pmessagequeue-> m_iwrite );
}

Return true;
}

 

// When the written subscript and the read subscript coincide, it indicates that no data is readable, and writing the subscript cannot catch up with the read subscript,
// The read subscript can overlap with the write subscript
Int ip_get_messagequeue (messagequeue * pmessagequeue)
{
Assert (null! = Pmessagequeue );

Int savewrite = pmessagequeue-> m_iwrite;

 
// No data readable
If (savewrite = pmessagequeue-> m_iread)
{
Return-1;
}
// Write the subscript before reading the next mark
Else if (savewrite> pmessagequeue-> m_iread)
{
Int iresult = (pmessagequeue-> m_parray) [pmessagequeue-> m_iread];
 
++ (Pmessagequeue-> m_iread );
 
Return iresult;
}
// Write the subscript after reading the next mark
Else
{
Int iresult = 0;
 
// Just read the end Of the Array
If (pmessagequeue-> m_iread = pmessagequeue-> m_ilength-1)
{
Iresult = (pmessagequeue-> m_parray) [pmessagequeue-> m_ilength-1];

Pmessagequeue-> m_iread = 0;

Return iresult;
}

Iresult = (pmessagequeue-> m_parray) [pmessagequeue-> m_iread];

++ (Pmessagequeue-> m_iread );
 
Return iresult;
}
}

Void ip_addlock_messagequeue (messagequeue * pmessagequeue)
{
Assert (null! = Pmessagequeue );

Pthread_mutex_lock (& (pmessagequeue-> m_mutex ));
}

Void ip_unlock_messagequeue (messagequeue * pmessagequeue)
{
Assert (null! = Pmessagequeue );

Pthread_mutex_unlock (& (pmessagequeue-> m_mutex ));
}

Void ip_signal_messagequeue (messagequeue * pmessagequeue)
{
Assert (null! = Pmessagequeue );

Pthread_cond_signal (& (pmessagequeue-> m_cond ));
}

Void ip_wait_messagequeue (messagequeue * pmessagequeue)
{
Assert (null! = Pmessagequeue );

Timespec mytime;
Mytime. TV _sec = Time (null) + 1; // wait for 1 second, must
Mytime. TV _nsec = 0;
 
Pthread_cond_timedwait (& (pmessagequeue-> m_cond), & (pmessagequeue-> m_mutex), (const struct timespec *) & mytime );
}

Bool ip_isempty_messagequeue (messagequeue * pmessagequeue)
{
Assert (null! = Pmessagequeue );

If (pmessagequeue-> m_iwrite = pmessagequeue-> m_iread)
{
Return true;
}
Else
{
Return false;
}
}

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.