blob: 7b722961690ea9ab33e66e5a99b13668e2252672 [file] [log] [blame]
Willy Tarreaubaaee002006-06-26 02:48:02 +02001/*
2 * AppSession functions.
3 *
4 * Copyright 2004-2006 Alexander Lazic, Klaus Wagner
Willy Tarreau26c25062009-03-08 09:38:41 +01005 * Copyright 2006-2009 Willy Tarreau
Willy Tarreaubaaee002006-06-26 02:48:02 +02006 *
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version
10 * 2 of the License, or (at your option) any later version.
11 *
12 */
13
14#include <stdio.h>
Willy Tarreau2dd0d472006-06-29 17:53:05 +020015#include <string.h>
Thierry FOURNIERac836ba2014-12-16 15:41:18 +010016#include <unistd.h>
Willy Tarreaubaaee002006-06-26 02:48:02 +020017
Willy Tarreau2dd0d472006-06-29 17:53:05 +020018#include <common/appsession.h>
Willy Tarreaue3ba5f02006-06-29 18:54:54 +020019#include <common/config.h>
Willy Tarreau63963c62007-05-13 21:29:55 +020020#include <common/memory.h>
Willy Tarreau51041c72007-09-09 21:56:53 +020021#include <common/sessionhash.h>
Willy Tarreau0c303ee2008-07-07 00:09:58 +020022#include <common/ticks.h>
Willy Tarreau2dd0d472006-06-29 17:53:05 +020023#include <common/time.h>
Willy Tarreaubaaee002006-06-26 02:48:02 +020024
Willy Tarreaubaaee002006-06-26 02:48:02 +020025#include <types/global.h>
Willy Tarreaubaaee002006-06-26 02:48:02 +020026
Willy Tarreauec6c5df2008-07-15 00:22:45 +020027#include <proto/proxy.h>
Willy Tarreaubaaee002006-06-26 02:48:02 +020028#include <proto/task.h>
29
Krzysztof Piotr Oledzkia643baf2008-05-29 23:53:44 +020030static struct task *appsess_refresh = NULL;
Willy Tarreau63963c62007-05-13 21:29:55 +020031struct pool_head *pool2_appsess;
Willy Tarreaubaaee002006-06-26 02:48:02 +020032struct app_pool apools;
33int have_appsession;
34
Willy Tarreaubaaee002006-06-26 02:48:02 +020035int appsession_init(void)
36{
37 static int initialized = 0;
38 int idlen;
39 struct server *s;
40 struct proxy *p = proxy;
41
42 if (!initialized) {
Willy Tarreau63963c62007-05-13 21:29:55 +020043 pool2_appsess = create_pool("appsess", sizeof(appsess), MEM_F_SHARED);
44 if (pool2_appsess == NULL)
45 return -1;
46
Willy Tarreaubaaee002006-06-26 02:48:02 +020047 if (!appsession_task_init()) {
Willy Tarreau63963c62007-05-13 21:29:55 +020048 int ser_msize, ses_msize;
49
Willy Tarreaubaaee002006-06-26 02:48:02 +020050 apools.sessid = NULL;
51 apools.serverid = NULL;
Willy Tarreau63963c62007-05-13 21:29:55 +020052
53 ser_msize = sizeof(void *);
54 ses_msize = sizeof(void *);
Willy Tarreaubaaee002006-06-26 02:48:02 +020055 while (p) {
56 s = p->srv;
Willy Tarreau63963c62007-05-13 21:29:55 +020057 if (ses_msize < p->appsession_len)
58 ses_msize = p->appsession_len;
Willy Tarreaubaaee002006-06-26 02:48:02 +020059 while (s) {
60 idlen = strlen(s->id);
Willy Tarreau63963c62007-05-13 21:29:55 +020061 if (ser_msize < idlen)
62 ser_msize = idlen;
Willy Tarreaubaaee002006-06-26 02:48:02 +020063 s = s->next;
64 }
65 p = p->next;
66 }
67 /* we use strings, so reserve space for '\0' */
Willy Tarreau63963c62007-05-13 21:29:55 +020068 ser_msize ++;
69 ses_msize ++;
70
71 apools.sessid = create_pool("sessid", ses_msize, MEM_F_SHARED);
72 if (!apools.sessid)
73 return -1;
74 apools.serverid = create_pool("serverid", ser_msize, MEM_F_SHARED);
75 if (!apools.serverid)
76 return -1;
Willy Tarreaubaaee002006-06-26 02:48:02 +020077 }
78 else {
79 fprintf(stderr, "appsession_task_init failed\n");
80 return -1;
81 }
82 initialized ++;
83 }
84 return 0;
85}
86
Simon Hormane8691762011-06-24 14:49:57 +090087static struct task *appsession_refresh(struct task *t)
Willy Tarreaubaaee002006-06-26 02:48:02 +020088{
Willy Tarreau51041c72007-09-09 21:56:53 +020089 struct proxy *p = proxy;
90 struct appsession_hash *htbl;
91 appsess *element, *back;
92 int i;
Willy Tarreaubaaee002006-06-26 02:48:02 +020093
94 while (p) {
95 if (p->appsession_name != NULL) {
96 htbl = &p->htbl_proxy;
Willy Tarreau51041c72007-09-09 21:56:53 +020097 as_hash_for_each_entry_safe(i, element, back, &p->htbl_proxy, hash_list) {
Willy Tarreau0c303ee2008-07-07 00:09:58 +020098 if (tick_is_expired(element->expire, now_ms)) {
Willy Tarreau51041c72007-09-09 21:56:53 +020099 if ((global.mode & MODE_DEBUG) &&
100 (!(global.mode & MODE_QUIET) || (global.mode & MODE_VERBOSE))) {
Willy Tarreau19d14ef2012-10-29 16:51:55 +0100101 chunk_printf(&trash, "appsession_refresh: cleaning up expired Session '%s' on Server %s\n",
102 element->sessid, element->serverid?element->serverid:"(null)");
Willy Tarreau89efaed2013-12-13 15:14:55 +0100103 shut_your_big_mouth_gcc(write(1, trash.str, trash.len));
Willy Tarreau51041c72007-09-09 21:56:53 +0200104 }
105 /* delete the expired element from within the hash table */
106 LIST_DEL(&element->hash_list);
107 htbl->destroy(element);
108 }/* end if (tv_isle(&asession->expire, &now)) */
Willy Tarreaubaaee002006-06-26 02:48:02 +0200109 }
110 }
111 p = p->next;
112 }
Willy Tarreau0c303ee2008-07-07 00:09:58 +0200113 t->expire = tick_add(now_ms, MS_TO_TICKS(TBLCHKINT)); /* check expiration every 5 seconds */
Willy Tarreau26c25062009-03-08 09:38:41 +0100114 return t;
Willy Tarreaubaaee002006-06-26 02:48:02 +0200115} /* end appsession_refresh */
116
Simon Hormane8691762011-06-24 14:49:57 +0900117int appsession_task_init(void)
118{
119 static int initialized = 0;
120 if (!initialized) {
121 if ((appsess_refresh = task_new()) == NULL)
122 return -1;
123
124 appsess_refresh->context = NULL;
125 appsess_refresh->expire = tick_add(now_ms, MS_TO_TICKS(TBLCHKINT));
126 appsess_refresh->process = appsession_refresh;
127 task_queue(appsess_refresh);
128 initialized ++;
129 }
130 return 0;
131}
132
Willy Tarreaubaaee002006-06-26 02:48:02 +0200133int match_str(const void *key1, const void *key2)
134{
135 appsess *temp1,*temp2;
136 temp1 = (appsess *)key1;
137 temp2 = (appsess *)key2;
138
139 //fprintf(stdout,">>>>>>>>>>>>>>temp1->sessid :%s:\n",temp1->sessid);
140 //fprintf(stdout,">>>>>>>>>>>>>>temp2->sessid :%s:\n",temp2->sessid);
141
142 return (strcmp(temp1->sessid,temp2->sessid) == 0);
143}/* end match_str */
144
Willy Tarreau51041c72007-09-09 21:56:53 +0200145void destroy(appsess *temp1) {
Willy Tarreau63963c62007-05-13 21:29:55 +0200146 pool_free2(apools.sessid, temp1->sessid);
Willy Tarreau63963c62007-05-13 21:29:55 +0200147 pool_free2(apools.serverid, temp1->serverid);
Willy Tarreau48d63db2008-08-03 17:41:33 +0200148 pool_free2(pool2_appsess, temp1);
Willy Tarreaubaaee002006-06-26 02:48:02 +0200149} /* end destroy */
150
151void appsession_cleanup( void )
152{
153 struct proxy *p = proxy;
154
155 while(p) {
Willy Tarreau51041c72007-09-09 21:56:53 +0200156 appsession_hash_destroy(&(p->htbl_proxy));
Willy Tarreaubaaee002006-06-26 02:48:02 +0200157 p = p->next;
158 }
Krzysztof Piotr Oledzkia643baf2008-05-29 23:53:44 +0200159
160 if (appsess_refresh) {
161 task_delete(appsess_refresh);
162 task_free(appsess_refresh);
163 appsess_refresh = NULL;
164 }
165
Willy Tarreaubaaee002006-06-26 02:48:02 +0200166}/* end appsession_cleanup() */
167
168
169
170/*
171 * Local variables:
172 * c-indent-level: 8
173 * c-basic-offset: 8
174 * End:
175 */