alloc-address.cc
上传用户:rrhhcc
上传日期:2015-12-11
资源大小:54129k
文件大小:6k
源码类别:

通讯编程

开发平台:

Visual C++

  1. /* -*- Mode:C++; c-basic-offset:8; tab-width:8; indent-tabs-mode:t -*- */
  2. /*
  3.  * Copyright (c) 1997 Regents of the University of California.
  4.  * All rights reserved.
  5.  * 
  6.  * Redistribution and use in source and binary forms, with or without
  7.  * modification, are permitted provided that the following conditions
  8.  * are met:
  9.  * 1. Redistributions of source code must retain the above copyright
  10.  *    notice, this list of conditions and the following disclaimer.
  11.  * 2. Redistributions in binary form must reproduce the above copyright
  12.  *    notice, this list of conditions and the following disclaimer in the
  13.  *    documentation and/or other materials provided with the distribution.
  14.  * 3. All advertising materials mentioning features or use of this software
  15.  *    must display the following acknowledgement:
  16.  *  This product includes software developed by the Daedalus Research
  17.  *  Group at the University of California Berkeley.
  18.  * 4. Neither the name of the University nor of the Research Group may be
  19.  *    used to endorse or promote products derived from this software without
  20.  *    specific prior written permission.
  21.  * 
  22.  * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
  23.  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  24.  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
  25.  * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
  26.  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  27.  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
  28.  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
  29.  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
  30.  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
  31.  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
  32.  * SUCH DAMAGE.
  33.  *
  34.  * $Header: /cvsroot/nsnam/ns-2/routing/alloc-address.cc,v 1.10 2000/09/14 18:19:25 haoboy Exp $
  35.  */
  36. /* functions invoked to allocate bits to the ns-address space */
  37. #include <stdlib.h>
  38. #include <assert.h>
  39. #include "config.h"
  40. #include <tclcl.h>
  41. class AllocAddr : public TclObject {
  42. public:
  43. AllocAddr();
  44. ~AllocAddr();
  45. int command(int argc, const char*const* argv);
  46. protected:
  47. void get_mask(nsmask_t *mask, int fieldsize);
  48. void alloc(int n);
  49. bool check_size(int n);
  50. bool find_free(int len, int *pos);
  51. bool test(int which);
  52. void set_field(int offset, int len, nsmask_t *mask, int *shift);
  53. void free_field(int len);
  54. void mark(int i);
  55. int size_;
  56. int *bitmap_;
  57. };
  58. class AllocAddrClass : public TclClass {
  59. public:
  60. AllocAddrClass() : TclClass("AllocAddr") {}
  61. TclObject* create(int, const char*const*) {
  62. return (new AllocAddr());
  63. }
  64. } AllocAddr_class;
  65. int AllocAddr::command(int argc, const char*const* argv)
  66. {
  67. int offset,
  68. addrsize,
  69. shift,
  70. fieldlen;
  71. nsmask_t mask;
  72. Tcl& tcl = Tcl::instance();
  73. if (argc == 3) {
  74. if (strcmp(argv[1], "freebit") == 0) {
  75. fieldlen = atoi(argv[2]);
  76. assert(fieldlen > 0);
  77. free_field(fieldlen);
  78. return (TCL_OK);
  79. }
  80. }
  81. else if (argc == 4) {
  82. if (strcmp(argv[1], "setbit") == 0) {
  83. fieldlen = atoi(argv[2]);
  84. addrsize = atoi(argv[3]);
  85. if (!check_size(addrsize)) {
  86. tcl.result("setbit: Size_ increased: Reallocate bits");
  87. return (TCL_ERROR);
  88. }
  89. if (!find_free(fieldlen, &offset)) {
  90. tcl.result("setbit: no contiguous space foundn");
  91. return (TCL_ERROR);
  92. }
  93. set_field(offset, fieldlen, &mask, &shift);
  94. // TESTING
  95. tcl.resultf("%d %d", mask, shift);
  96. return (TCL_OK);
  97. }
  98. }
  99. else if (argc == 5) {
  100. int oldfldlen;
  101. if (strcmp(argv[1], "expand-port") == 0) {
  102. fieldlen = atoi(argv[2]);
  103. addrsize = atoi(argv[3]);
  104. oldfldlen = atoi(argv[4]);
  105. if (!check_size(addrsize)) {
  106. tcl.result("expand-port: Size_ increased: Reallocate bits");
  107. return (TCL_ERROR);
  108. }
  109. if (!find_free(fieldlen, &offset)) {
  110. tcl.result("expand-port: no contiguous space foundn");
  111. return (TCL_ERROR);
  112. }
  113. int i, k;
  114. for (i = offset, k = 0; k < fieldlen; k++, i--) {
  115. bitmap_[i] = 1;
  116. }
  117. shift = offset - (fieldlen - 1);
  118. get_mask(&mask, fieldlen + oldfldlen);
  119. // TESTING
  120. tcl.resultf("%d %d", mask, shift);
  121. return (TCL_OK);
  122. }
  123. }
  124. return TclObject::command(argc, argv);
  125. }
  126. AllocAddr::AllocAddr()
  127. {
  128. size_ = 0;
  129. bitmap_ = 0;
  130. }
  131. AllocAddr::~AllocAddr()
  132. {
  133. delete [] bitmap_;
  134. }
  135. void AllocAddr::alloc(int n)
  136. {
  137. size_ = n;
  138. bitmap_ = new int[n];
  139. for (int i=0; i < n; i++)
  140. bitmap_[i] = 0;
  141. }
  142. bool AllocAddr::check_size(int n)
  143. {
  144. if (n <= size_)
  145. return 1;
  146. assert (n > 0);
  147. if (size_ == 0) {
  148. alloc(n);
  149. return 1;
  150. }
  151. if (n > size_) 
  152. return 0;
  153. return 1;
  154. // this check is no longer needed, as now bits are re-allocated every time
  155. // the size changes.
  156. //     int *old = bitmap_;
  157. //     int osize = size_;
  158. //     alloc(n);
  159. //     for (int i = 0; i < osize; i++) 
  160. //  bitmap_[i] = old[i];
  161. //     delete [] old;
  162. }
  163. void AllocAddr::mark(int i)
  164. {
  165. bitmap_[i] = 1;
  166. }
  167. void AllocAddr::get_mask(nsmask_t *mask, int fieldsize)
  168. {
  169. // int temp = (int)(pow(2, (double)fieldsize));
  170. *mask = (1 << fieldsize) - 1;
  171. }
  172. bool AllocAddr::test(int which)
  173. {
  174. assert(which <= size_);
  175. if (bitmap_[which] == 1)
  176. return TRUE;
  177. else
  178. return FALSE;
  179. }
  180. bool AllocAddr::find_free(int len, int *pos) 
  181. {
  182. int count = 0;
  183. int temp = 0;
  184. for (int i = (size_ - 1); i >= 0; i--)
  185. if (!test(i)) {
  186. /**** check if n contiguous bits are free ****/
  187. temp = i;
  188. for (int k = 0; (k < len) && (i >=0); k++, i--){
  189. if(test(i)) {
  190. count = 0;
  191. break;
  192. }
  193. count++;
  194. }
  195. if (count == len) {
  196. *pos = temp;
  197. return 1;
  198. }
  199. }
  200. return 0;
  201. }
  202. void AllocAddr::set_field(int offset, int len, nsmask_t *mask, int *shift)
  203. {
  204. int i, k;
  205. for (k = 0, i = offset; k < len; k++, i--) {
  206. bitmap_[i] = 1; 
  207. }
  208. *shift = offset - (len-1);
  209. get_mask(mask, len);
  210. }
  211. void AllocAddr::free_field(int len)
  212. {
  213. int count = 0;
  214. for (int i = 0; i < size_; i++) {
  215. if (test(i)) {
  216. bitmap_[i] = 0;
  217. count++;
  218. }
  219. if (count == len)
  220. break;
  221. }
  222. }