~ubuntu-branches/ubuntu/wily/sflphone/wily

« back to all changes in this revision

Viewing changes to daemon/libs/pjproject-2.2.1/pjlib/src/pj/fifobuf.c

  • Committer: Package Import Robot
  • Author(s): Jonathan Riddell
  • Date: 2015-01-07 14:51:16 UTC
  • mfrom: (4.3.5 sid)
  • Revision ID: package-import@ubuntu.com-20150107145116-yxnafinf4lrdvrmx
Tags: 1.4.1-0.1ubuntu1
* Merge with Debian, remaining changes:
 - Drop soprano, nepomuk build-dep
* Drop ubuntu patches, now upstream

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* $Id: fifobuf.c 4537 2013-06-19 06:47:43Z riza $ */
 
2
/* 
 
3
 * Copyright (C) 2008-2011 Teluu Inc. (http://www.teluu.com)
 
4
 * Copyright (C) 2003-2008 Benny Prijono <benny@prijono.org>
 
5
 *
 
6
 * This program is free software; you can redistribute it and/or modify
 
7
 * it under the terms of the GNU General Public License as published by
 
8
 * the Free Software Foundation; either version 2 of the License, or
 
9
 * (at your option) any later version.
 
10
 *
 
11
 * This program is distributed in the hope that it will be useful,
 
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
14
 * GNU General Public License for more details.
 
15
 *
 
16
 * You should have received a copy of the GNU General Public License
 
17
 * along with this program; if not, write to the Free Software
 
18
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA 
 
19
 */
 
20
#include <pj/fifobuf.h>
 
21
#include <pj/log.h>
 
22
#include <pj/assert.h>
 
23
#include <pj/os.h>
 
24
 
 
25
#define THIS_FILE   "fifobuf"
 
26
 
 
27
#define SZ  sizeof(unsigned)
 
28
 
 
29
PJ_DEF(void) pj_fifobuf_init (pj_fifobuf_t *fifobuf, void *buffer, unsigned size)
 
30
{
 
31
    PJ_CHECK_STACK();
 
32
 
 
33
    PJ_LOG(6, (THIS_FILE, 
 
34
               "fifobuf_init fifobuf=%p buffer=%p, size=%d", 
 
35
               fifobuf, buffer, size));
 
36
 
 
37
    fifobuf->first = (char*)buffer;
 
38
    fifobuf->last = fifobuf->first + size;
 
39
    fifobuf->ubegin = fifobuf->uend = fifobuf->first;
 
40
    fifobuf->full = 0;
 
41
}
 
42
 
 
43
PJ_DEF(unsigned) pj_fifobuf_max_size (pj_fifobuf_t *fifobuf)
 
44
{
 
45
    unsigned s1, s2;
 
46
 
 
47
    PJ_CHECK_STACK();
 
48
 
 
49
    if (fifobuf->uend >= fifobuf->ubegin) {
 
50
        s1 = (unsigned)(fifobuf->last - fifobuf->uend);
 
51
        s2 = (unsigned)(fifobuf->ubegin - fifobuf->first);
 
52
    } else {
 
53
        s1 = s2 = (unsigned)(fifobuf->ubegin - fifobuf->uend);
 
54
    }
 
55
    
 
56
    return s1<s2 ? s2 : s1;
 
57
}
 
58
 
 
59
PJ_DEF(void*) pj_fifobuf_alloc (pj_fifobuf_t *fifobuf, unsigned size)
 
60
{
 
61
    unsigned available;
 
62
    char *start;
 
63
 
 
64
    PJ_CHECK_STACK();
 
65
 
 
66
    if (fifobuf->full) {
 
67
        PJ_LOG(6, (THIS_FILE, 
 
68
                   "fifobuf_alloc fifobuf=%p, size=%d: full!", 
 
69
                   fifobuf, size));
 
70
        return NULL;
 
71
    }
 
72
 
 
73
    /* try to allocate from the end part of the fifo */
 
74
    if (fifobuf->uend >= fifobuf->ubegin) {
 
75
        available = (unsigned)(fifobuf->last - fifobuf->uend);
 
76
        if (available >= size+SZ) {
 
77
            char *ptr = fifobuf->uend;
 
78
            fifobuf->uend += (size+SZ);
 
79
            if (fifobuf->uend == fifobuf->last)
 
80
                fifobuf->uend = fifobuf->first;
 
81
            if (fifobuf->uend == fifobuf->ubegin)
 
82
                fifobuf->full = 1;
 
83
            *(unsigned*)ptr = size+SZ;
 
84
            ptr += SZ;
 
85
 
 
86
            PJ_LOG(6, (THIS_FILE, 
 
87
                       "fifobuf_alloc fifobuf=%p, size=%d: returning %p, p1=%p, p2=%p", 
 
88
                       fifobuf, size, ptr, fifobuf->ubegin, fifobuf->uend));
 
89
            return ptr;
 
90
        }
 
91
    }
 
92
 
 
93
    /* try to allocate from the start part of the fifo */
 
94
    start = (fifobuf->uend <= fifobuf->ubegin) ? fifobuf->uend : fifobuf->first;
 
95
    available = (unsigned)(fifobuf->ubegin - start);
 
96
    if (available >= size+SZ) {
 
97
        char *ptr = start;
 
98
        fifobuf->uend = start + size + SZ;
 
99
        if (fifobuf->uend == fifobuf->ubegin)
 
100
            fifobuf->full = 1;
 
101
        *(unsigned*)ptr = size+SZ;
 
102
        ptr += SZ;
 
103
 
 
104
        PJ_LOG(6, (THIS_FILE, 
 
105
                   "fifobuf_alloc fifobuf=%p, size=%d: returning %p, p1=%p, p2=%p", 
 
106
                   fifobuf, size, ptr, fifobuf->ubegin, fifobuf->uend));
 
107
        return ptr;
 
108
    }
 
109
 
 
110
    PJ_LOG(6, (THIS_FILE, 
 
111
               "fifobuf_alloc fifobuf=%p, size=%d: no space left! p1=%p, p2=%p", 
 
112
               fifobuf, size, fifobuf->ubegin, fifobuf->uend));
 
113
    return NULL;
 
114
}
 
115
 
 
116
PJ_DEF(pj_status_t) pj_fifobuf_unalloc (pj_fifobuf_t *fifobuf, void *buf)
 
117
{
 
118
    char *ptr = (char*)buf;
 
119
    char *endptr;
 
120
    unsigned sz;
 
121
 
 
122
    PJ_CHECK_STACK();
 
123
 
 
124
    ptr -= SZ;
 
125
    sz = *(unsigned*)ptr;
 
126
 
 
127
    endptr = fifobuf->uend;
 
128
    if (endptr == fifobuf->first)
 
129
        endptr = fifobuf->last;
 
130
 
 
131
    if (ptr+sz != endptr) {
 
132
        pj_assert(!"Invalid pointer to undo alloc");
 
133
        return -1;
 
134
    }
 
135
 
 
136
    fifobuf->uend = ptr;
 
137
    fifobuf->full = 0;
 
138
 
 
139
    PJ_LOG(6, (THIS_FILE, 
 
140
               "fifobuf_unalloc fifobuf=%p, ptr=%p, size=%d, p1=%p, p2=%p", 
 
141
               fifobuf, buf, sz, fifobuf->ubegin, fifobuf->uend));
 
142
 
 
143
    return 0;
 
144
}
 
145
 
 
146
PJ_DEF(pj_status_t) pj_fifobuf_free (pj_fifobuf_t *fifobuf, void *buf)
 
147
{
 
148
    char *ptr = (char*)buf;
 
149
    char *end;
 
150
    unsigned sz;
 
151
 
 
152
    PJ_CHECK_STACK();
 
153
 
 
154
    ptr -= SZ;
 
155
    if (ptr < fifobuf->first || ptr >= fifobuf->last) {
 
156
        pj_assert(!"Invalid pointer to free");
 
157
        return -1;
 
158
    }
 
159
 
 
160
    if (ptr != fifobuf->ubegin && ptr != fifobuf->first) {
 
161
        pj_assert(!"Invalid free() sequence!");
 
162
        return -1;
 
163
    }
 
164
 
 
165
    end = (fifobuf->uend > fifobuf->ubegin) ? fifobuf->uend : fifobuf->last;
 
166
    sz = *(unsigned*)ptr;
 
167
    if (ptr+sz > end) {
 
168
        pj_assert(!"Invalid size!");
 
169
        return -1;
 
170
    }
 
171
 
 
172
    fifobuf->ubegin = ptr + sz;
 
173
 
 
174
    /* Rollover */
 
175
    if (fifobuf->ubegin == fifobuf->last)
 
176
        fifobuf->ubegin = fifobuf->first;
 
177
 
 
178
    /* Reset if fifobuf is empty */
 
179
    if (fifobuf->ubegin == fifobuf->uend)
 
180
        fifobuf->ubegin = fifobuf->uend = fifobuf->first;
 
181
 
 
182
    fifobuf->full = 0;
 
183
 
 
184
    PJ_LOG(6, (THIS_FILE, 
 
185
               "fifobuf_free fifobuf=%p, ptr=%p, size=%d, p1=%p, p2=%p", 
 
186
               fifobuf, buf, sz, fifobuf->ubegin, fifobuf->uend));
 
187
 
 
188
    return 0;
 
189
}