001/* jpvmMessageQueue.java
002 *
003 * The jpvmMessageQueue class implements a searchable database
004 * of jpvm messages. The database can be searched by message tag,
005 * source process, both, or neither (i.e. wildcard search).
006 *
007 * Adam J Ferrari
008 * Sat 05-25-1996
009 *
010 * Copyright (C) 1996  Adam J Ferrari
011 * 
012 * This library is free software; you can redistribute it and/or
013 * modify it under the terms of the GNU Library General Public
014 * License as published by the Free Software Foundation; either
015 * version 2 of the License, or (at your option) any later version.
016 * 
017 * This library is distributed in the hope that it will be useful,
018 * but WITHOUT ANY WARRANTY; without even the implied warranty of
019 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
020 * Library General Public License for more details.
021 * 
022 * You should have received a copy of the GNU Library General Public
023 * License along with this library; if not, write to the
024 * Free Software Foundation, Inc., 675 Mass Ave, Cambridge,
025 * MA 02139, USA.
026 */
027
028package jpvm;
029
030class jpvmMessageQueueElement {
031        public  jpvmMessage             message;
032        public  jpvmMessageQueueElement next;
033
034        public jpvmMessageQueueElement() {
035                message = null;
036                next    = null;
037        }
038
039        public jpvmMessageQueueElement(jpvmMessage m) {
040                message = m;
041                next    = null;
042        }
043};
044
045public
046class jpvmMessageQueue {
047        private jpvmMessageQueueElement list_head;
048        private jpvmMessageQueueElement list_tail;
049
050        private synchronized void addElement(jpvmMessageQueueElement nw) {
051                if(list_head == null) {
052                        list_head = list_tail = nw;
053                        return;
054                }
055                list_tail.next = nw;
056                list_tail = nw;
057        }
058
059        private synchronized void deleteElement(jpvmMessageQueueElement d) {
060                if(list_head == null) return;
061                if(list_head == d) {
062                        // Deleting head element.
063                        list_head = d.next;
064                        if(list_tail == d) list_tail=null;
065                        return;
066                }
067                jpvmMessageQueueElement tmp = list_head;
068                while(tmp.next != d) {
069                        tmp = tmp.next;
070                        if(tmp == null) {
071                                // Element wasn't in the list
072                                return;
073                        }
074                }
075                tmp.next = d.next;
076                if(list_tail==d) list_tail=tmp;
077        }
078
079        private synchronized jpvmMessageQueueElement find() {
080                return list_head;
081        }
082
083        private synchronized jpvmMessageQueueElement find(int tag) {
084                jpvmMessageQueueElement tmp = list_head;
085                while (tmp != null) {
086                        if(tmp.message.messageTag == tag) return tmp;
087                        tmp = tmp.next;
088                }
089                return null;
090        }
091
092        private synchronized jpvmMessageQueueElement find(jpvmTaskId tid) {
093                jpvmMessageQueueElement tmp = list_head;
094                while (tmp != null) {
095                        if(tmp.message.sourceTid.equals(tid)) return tmp;
096                        tmp = tmp.next;
097                }
098                return null;
099        }
100
101        private synchronized jpvmMessageQueueElement find(jpvmTaskId tid, 
102            int tag) {
103                jpvmMessageQueueElement tmp = list_head;
104                while (tmp != null) {
105                        if((tmp.message.sourceTid.equals(tid)) && 
106                           (tmp.message.messageTag==tag))
107                                return tmp;
108                        tmp = tmp.next;
109                }
110                return null;
111        }
112
113        public jpvmMessageQueue() {
114                list_head = list_tail = null;
115        }
116
117        public synchronized void enqueue(jpvmMessage m) {
118                jpvmMessageQueueElement nw = new jpvmMessageQueueElement(m);
119                addElement(nw);
120                notifyAll();
121        }
122
123        public synchronized boolean probe() {
124                jpvmMessageQueueElement tmp = find();
125                return (tmp != null);
126        }
127
128        public synchronized boolean probe(int tag) {
129                jpvmMessageQueueElement tmp = find(tag);
130                return (tmp != null);
131        }
132
133        public synchronized boolean probe(jpvmTaskId tid) {
134                jpvmMessageQueueElement tmp = find(tid);
135                return (tmp != null);
136        }
137
138        public synchronized boolean probe(jpvmTaskId tid, int tag) {
139                jpvmMessageQueueElement tmp = find(tid, tag);
140                return (tmp != null);
141        }
142
143        public synchronized jpvmMessage dequeue() {
144                jpvmMessageQueueElement tmp = null;
145                while(true) {
146                        if((tmp = find())!=null) {
147                                deleteElement(tmp);
148                                return tmp.message;
149                        }
150                        try {
151                                wait();
152                        }
153                        catch (InterruptedException ie) {
154                        }
155                }
156        }
157
158        public synchronized jpvmMessage dequeue(int tag) {
159                jpvmMessageQueueElement tmp = null;
160                while(true) {
161                        if((tmp = find(tag))!=null) {
162                                deleteElement(tmp);
163                                return tmp.message;
164                        }
165                        try {
166                                wait();
167                        }
168                        catch (InterruptedException ie) {
169                        }
170                }
171        }
172
173        public synchronized jpvmMessage dequeue(jpvmTaskId tid) {
174                jpvmMessageQueueElement tmp = null;
175                while(true) {
176                        if((tmp = find(tid))!=null) {
177                                deleteElement(tmp);
178                                return tmp.message;
179                        }
180                        try {
181                                wait();
182                        }
183                        catch (InterruptedException ie) {
184                        }
185                }
186        }
187
188        public synchronized jpvmMessage dequeue(jpvmTaskId tid, int tag) {
189                jpvmMessageQueueElement tmp = null;
190                while(true) {
191                        if((tmp = find(tid,tag))!=null) {
192                                deleteElement(tmp);
193                                return tmp.message;
194                        }
195                        try {
196                                wait();
197                        }
198                        catch (InterruptedException ie) {
199                        }
200                }
201        }
202
203        public synchronized jpvmMessage dequeueNonBlock() {
204                jpvmMessageQueueElement tmp = find();
205                if(tmp != null) {
206                        deleteElement(tmp);
207                        return tmp.message;
208                }
209                return null;
210        }
211
212        public synchronized jpvmMessage dequeueNonBlock(int tag) {
213                jpvmMessageQueueElement tmp = find(tag);
214                if(tmp != null) {
215                        deleteElement(tmp);
216                        return tmp.message;
217                }
218                return null;
219        }
220
221        public synchronized jpvmMessage dequeueNonBlock(jpvmTaskId tid) {
222                jpvmMessageQueueElement tmp = find(tid);
223                if(tmp != null) {
224                        deleteElement(tmp);
225                        return tmp.message;
226                }
227                return null;
228        }
229
230        public synchronized jpvmMessage dequeueNonBlock(jpvmTaskId tid,int tag){
231                jpvmMessageQueueElement tmp = find(tid,tag);
232                if(tmp != null) {
233                        deleteElement(tmp);
234                        return tmp.message;
235                }
236                return null;
237        }
238};