blob: 5578130de844eba22fccd76aeff98fa6539a80bd [file] [log] [blame]
Harald Welteb68899d2009-01-06 21:47:18 +00001/* Paging helper and manager.... */
2/* (C) 2009 by Holger Hans Peter Freyther <zecke@selfish.org>
3 * All Rights Reserved
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 */
20
21/*
22 * Relevant specs:
23 * 12.21:
24 * - 9.4.12 for CCCH Local Threshold
25 *
26 * 05.58:
27 * - 8.5.2 CCCH Load indication
28 * - 9.3.15 Paging Load
29 *
30 * Approach:
31 * - Send paging command to subscriber
32 * - On Channel Request we will remember the reason
33 * - After the ACK we will request the identity
34 * - Then we will send assign the gsm_subscriber and
35 * - and call a callback
36 */
37
38#include <openbsc/paging.h>
39#include <openbsc/debug.h>
40
41static LLIST_HEAD(managed_bts);
42
43static int page_pending_request(struct paging_bts *bts,
44 struct gsm_subscriber *subscr) {
45 struct paging_request *req;
46
47 llist_for_each_entry(req, &bts->pending_requests, entry) {
48 if (subscr == req->subscr)
49 return 1;
50 }
51
52 return 0;
53}
54
55struct paging_bts* page_allocate(struct gsm_bts *bts) {
56 struct paging_bts *page;
57
58 page = (struct paging_bts *)malloc(sizeof(*page));
59 memset(page, 0, sizeof(*page));
60 llist_add_tail(&page->bts_list, &managed_bts);
61
62 return page;
63}
64
65void page_request(struct gsm_bts *bts, struct gsm_subscriber *subscr) {
66 struct paging_bts *bts_entry;
67 struct paging_request *req;
68
69 req = (struct paging_request *)malloc(sizeof(*req));
70 req->subscr = subscr_get(subscr);
71 req->bts = bts;
72
73 llist_for_each_entry(bts_entry, &managed_bts, bts_list) {
74 if (bts == bts_entry->bts && !page_pending_request(bts_entry, subscr)) {
75 llist_add_tail(&req->entry, &bts_entry->pending_requests);
76 return;
77 }
78 }
79
80 DEBUGP(DPAG, "Paging request for not mnaged BTS\n");
81 free(req);
82 return;
83}