Study of Complex handoff in context of Simple and Dual Homing of RNC’s on a Random Mobility Introduction: This paper deals with the analysis of the rates of complex handoff in context of the single homing and dual homing of the RNC’s. With random Single Homed model and the corresponding Dual Home model generated using two meta-heuristic techniques, namely Simulated Annealing (SA), Tabu search (TS)and then the mobile node was allowed to make random movements throughout the topology and thus register its handoffs which has been analysed to get to know the performance of the system during normal times when the us ers do-don’t show up particular mobility patters.

Handoffs: SIMPLEST HANDOFFS : When the MS moves from cells controlled by the same BSC (intraBSC inter-cell handoff) then this is considered to be the simplest handoff.

RNC

MS

SIMPLE HANDOFFS : When the MS moves from cells controlled Cells under the same MSC but controlled by different BSCs (intra-MSC inter-BSC handoff) then this is considered to be a simple handoff.

NODE B

NODE B

MSC RNC

RNC

NODE B

NODE B

MS

COMPLEX HANDOFFS : When the MS moves from cells controlled by different MSCs (interMSC handoff) then this case is considered to be a complex handoff.

MSC

MSC

RNC

RNC

NODE B

NODE B

MS

REDUCING COMPLEX HANDOFF TO S IMPL E HANDOFFS Now when the MS moves from first NODE B to second NODE B, the handoff is reduced from a COMPLEX CASE to a SIMPLE CASE.

MSC

MSC

RNC

RNC

NODE B

NODE B

MS

The Mobility Model: The mobility model that was put into test was random movement model, which is considered to be the worst case model for any network. And the results of the MS movements and the corresponding handoff costs were analysed for both the currently implemented single home networks and our proposed dual home networks. The results show drastic decreas e of complex handoff’s thus showing the success of the dual home architecture. The details of the model:RANDOM WALK ALGORITHM: The random walk is generated taking in consideration the various parameters. Each of the paramemter has been discussed in the following points. Cell Resident Time: The Cell resident time was made random, so as to implement the realtime movement of a mobile equipment. For example a person carring a mobile starts of a journey from his home town to his office. So during this he travels by bus. Since the time taken by bus can never be accurately estimated due to the uncertainity of the roads so the cell resident time has been made random.

Pseudo Code for Cell Resident Time: ************************************************************************************************ wait_for = rand() % 50; // Limiting the maximum resident time to 50 Sleep( wait_for ); ************************************************************************************************ Speed & Direction: The Average Speed of motion is mainly determined by the Cell Resident time. In this case the Direction is determined randomly. We have implemented a matrix type mapped topology of the real hexagonal topology. So the cell onto which the ms can move onto is given by the formulae 1

D  (i  k )2  ( j  l ) 2  (i  k )  ( j  l )

Where (i,j) and (k,l) refers to present co-ordinate and the next co-ordinate respectively. If D <= 1 then this cell refers to an adjacent cell on the Hexagonal grid, so the mobile node can move onto it. So in order to move randomly the computer randomly chooses a neighboring cell and checks whether that cell is really a neighbor in hexagonal grid or not. If not then it check again a random cell in its matrix neigbouhood. It moves to the first neighbour cell that it finds Pseudo Code for Direction: ************************************************************************************************ Step 1: If current position is (m,n) on the matrix grid. Generate a ra ndom number between (m-1, n-1) and (m+1,n+1) Step 2: Check if that cell is really a neighbor or not. If Neighbor Move onto that cell Else Repeat Step 1; *********************************************************************************************** Duration of Random walk: The duration of random walk depends on the user input. The input can be for how much time the random walk will go on for, or the input determines the maximum number of handoffs possible.

1

A Heuristic Technique for Solving Dual -Homing Assignment Problem of 2.5 G Cellular Networks , Appendix I

Stimulation Model: The stimulation was done on a using C++ and OpenCV (Open Source Image Manipulation Library). The mobile element was allowed to move about randomly throughout the cells of the NODEB’s and the handoffs were recorded. The number of handoffs and their corresponding types were then analysed from the recorded data. Various parameters had been taken into consideration from normal Cell Resident time, Speed and Direction to the size of the mobile space, i.e. the size of the networks. As discussed earlier about the parameters a C++ code was written which had been run to stimulate the environment. The pattern of movements had been recorded and some of them have been presented in the following page.

SOME OF THE RECORDED MOVEMENTS OF THE RANDOM MOBILITY PATTERN

Analysis of the outputs The random mobility models did show up a lot of reduction in the complex handoff rates and even there was a case where this dropped to 0% i.e all complex handoffs reduced to simple handoff. Some of the Results that showed up are presented through the follo wing graphs.

Handoffs with Change in Grid Size 100.00% 90.00%

% of Handoffs

80.00%

70.00%

Simplest Single Homed

60.00%

Simple Single Homed

50.00%

40.00%

Complex Single Homed

30.00%

Simplest Dual Homed

20.00%

Simple Dual Homed

10.00%

Complex Dual Homed

0.00%

20x20

25x25

30x30

40x40

Topology Grid Size

Analyzing the above figure it can be said that the number of handoffs doesn’t depend on the topology size. It remains almost constant throughout, though dual homing showed a drop in the number of complex handoff increasing the rate of simple handoffs which is intended.

Plotting the percentage handoffs when the no of handoffs got changed i.e. when the speed of the mobile element was varying the results obtained are…

Analysis with changing number of Handoffs 60.00%

% of Handoffs

50.00% 40.00%

Simplest Single Homed Simple Single homed

30.00%

Complex Single homed 20.00%

Simpled Dual Homed

10.00%

Simple Dual Homed Complex Dual Homed

0.00% 100

250

500

750

1000

2000

5000

Total Number of Handoffs

Analyzing the graph it is found that the dual homing of RNC’s performed very well with varying no of handoffs. There was a huge drop in case of complex handoffs and corresponding increase in case of simple handoffs.

Conclusion: After analyzing various cases and possibilities of the handoff situations the overall reduction in complex handoff’s in case of random model

Simplest Handoff’s Simple Handoff’s Complex handoff’s

Single Home 57.66% 27.105% 14.95%

Dual Homed 57.17 28.65 13.04%

Representing the Above Data in Graphical Format 70.00% 60.00%

% of handoff's

50.00% 40.00% Single Homed

30.00%

Dual Homed 20.00% 10.00%

0.00% Simplest

Simple

Complex

Type of Handoff

Thus with the dual homing model helps in reduction in the complex handoff even when the MS mobility patters does not refer to the general trend. Thus in a single line , dual homing performs good even in case of random mobility pattern.

Kinshuk Bairagi [email protected]

APPENDIX I

APPENDIX II The C++ Code /***************************************************************************** Program By KINSHUK BAIRAGI This program stimulates the random mobility pattern of the MS within the NODEB's ******************************************************************************/ #include #include #include #include #include #include #include #include #include #include #include

"stdafx.h"

#include #include #include //using namespace std; #define DISPLAY_ON_SCREEN it 0 */ #define DISPLAY_IMAGE */ #define TOT_HAND

1

/* set it 1 to check out process while in progress else set

0

/* set it to 1 to check the visual simulation else set it 0

5000

/* THIS SETS THE TOTAL NO OF MAX HANDOFFS POSSIBLE */

class MSC { /* -------------------------------------------- ------------------------------------------------This class implements the MSC's -------------------------------------------- ------------------------------------------------*/ public: int msc_id; int nodeb_id; /* position in which the msc is situated */ int msc_cap; /* max capacity of msc to handle nodeb traffic */ }; class RNC { /* -------------------------------------------- ------------------------------------------------This class implements the RNC's --------------------------------------------------------------------------------------------*/ public: int rnc_id; int nodeb_id; /* position in which the rnc is situated int * sgsn_id; * */ int msc_id; int int float

msc2_id; rnc_cap; d2_cost;

/* due to dual homing */ /* capacity of rnc to handle nodeb traffic */ /* distance from rnc to its sgsn */

/* ========================================================================================

RNC_init() initialises the RNC objets with negetive or default msc_id's ======================================================================================== */ void RNC_init()

{ msc_id = -1; msc2_id = -1; }

} ; class NODEB { /* -------------------------------------------- ------------------------------------------------This class implements the NODEB's -------------------------------------------- ------------------------------------------------*/ public: int nodeb_id; int nodeb_x; int nodeb_y; int rnc_id; /* keeps the RNC id for each nodeB. */ int nodeb_cap; /* nodeb capacity */ float d1_cost; /* distance from nodeb to its rnc */ }; /* Global variables */ NODEB *nodeb; RNC *rnc; MSC *msc; int char

no_of_nodeb, no_of_rnc, no_of_msc; buffer[20480];

int int

*handoffcost[4]; **nodebarray, nodebarray_row, nodebarray_col;

IplImage

*img = 0;

char

filename[255];

int char

PRGM_ID; PRGM_TID[10];

/* ============================================================================================ void explode10(char mytext[], char output[][100] , char delim = ' ') This function explodes the input string into array of strings based on the delimter which is by default space ============================================================================================ */ void explode10(char mytext[], char output[][100] , char delim = ' ') { /*~~~~~~~~~~~~~~~~~~~~~~~~~~*/ char buffer[20480]; /* max 1024 chars */ long int i = 0, icount = 0; int k = 0; /*~~~~~~~~~~~~~~~~~~~~~~~~~~*/ for(icount = 0; mytext[icount] != '\0'; icount++) { if(mytext[icount] != delim ) { buffer[i] = mytext[icount]; i++; } else { buffer[i] = '\0'; strcpy(output[k], buffer); i = 0;

k++; } } buffer[i] = '\0'; strcpy(output[k], buffer);

/* save the last one */ /* save the last one */

} /* ============================================================================================ void delay(float sec) This funcion makes the progarm wait for sec seconds. ============================================================================================ */ void delay(float sec) { for(time_t t = time(NULL) + sec; time(NULL) < t;); } /* ============================================================================================ void alert(int freq = 1) This function generates audible alert. ============================================================================================ */ void alert(int freq = 1) { for ( int i = 0; i < freq; i++ ) printf( "\a" ); } /* ============================================================================================ void readfile(ifstream fp) This function does all the input file handling operations Parses the entire input file and convers into variables for the programs future use ============================================================================================ */ void readfile(ifstream fp) { /** * ASSUMING THE INPUT FILE CONTAINS DATA IN THE FOLLOWING FORMAT MAX_NO_OF_NODEBS, MAX_NO_OF_RNCS, MAX_NO_OF_SGSNS * nodeb_cap(1), ...... nodeb_cap(n) rnc_cap(1), ..... rnc_cap(n) sgsn_cvp(1), ..... sgsn_cap(n) no_of_nodeb_rnc_link * nodeb_no,rnc_no ....... no_of_rnc_sgsn_link rnc_no,sgsn_no ..... no_of_amo_cost_nodeb_rnc nodeb_no,rnc_no,amo_cost * ...... no_of_amo_cost_rnc_sgsn rnc_no,sgsn_no,amo_cost ..... no_of_nodeb_nodeb_handoff * nodeb_no1,nodeb_no2,handoff_cost */ char output[1024][100]; int readlines, i, nodeb_no, rnc_no, msc_no; fp.getline(buffer, 2048); explode10(buffer, output); no_of_nodeb = atoi(output[0]); nodeb = (NODEB *) malloc((no_of_nodeb + 1) * sizeof(NODEB));

/* alocate memory */

/* * nodeb_array = ( _3DLAYER * )malloc( (no_of_nodeb + 1) * sizeof(_3DLAYER) ); * //alocate memory for the 3dlayer mapping */ no_of_rnc = atoi(output[1]); rnc = (RNC *) malloc((no_of_rnc + 1) * sizeof(RNC)); /* alocate memory */ for(i = 1; i <= no_of_rnc + 1; i++) rnc[i].RNC_init(); no_of_msc = atoi(output[2]); msc = (MSC *) malloc((no_of_msc + 1) * sizeof(MSC)); memory */

/* alocate

fp.getline(buffer, 20480); fp.getline(buffer, 20480); fp.getline(buffer, 20480);

/* this line gets the capacites of nodeb */ /* this line gets the capacites of rnc */ /* this line gets the capacites of msc */

fp.getline(buffer, 2048); explode10(buffer, output); readlines = atoi(output[0]); /* no of nodeb rnc links */ for(i = 1; i <= readlines; i++) { fp.getline(buffer, 2048); explode10(buffer, output); nodeb_no = atoi(output[0]); rnc_no = atoi(output[1]); nodeb[nodeb_no].rnc_id = rnc_no; } /* * for ( i = 1; * i <= readlines; * i++ ) cout<<" NODE B no:"<< i << "connected to rnc " <
rnc[rnc_no].msc2_id = msc_no;

/* dual home rnc msc links */

} /* * for ( i = 1; * i <= rnc_no; * i++ ) { cout<<" rnc no:"<< i << "connected to msc " <
/* no of amo cost lines */

/* do amo cost rnc msc reading here */ } fp.getline(buffer, 2048); explode10(buffer, output); readlines = atoi(output[0]);

/* no of handoff lines */

for(i = 1; i <= 3; i++) handoffcost[i] = (int *) malloc(readlines * sizeof(int)); /* alocate memory */ for(i = 1; i <= readlines; i++)

{ fp.getline(buffer, 2048); explode10(buffer, output); handoffcost[1][i] = atoi(output[0]); handoffcost[2][i] = atoi(output[1]); handoffcost[3][i] = atoi(output[2]); } /* JOB COMPLETE */ return; } /* ============================================================================================ this function calculates the handoff cost and returns: 1 if less than simplest i.e within same nodeb 2 if simplest 3 if simple 4 if complex ============================================================================================ */ double handoff_cost(NODEB a, NODEB b) { static int reduced_complex = 0; int a_nodeb = a.nodeb_id; int b_nodeb = b.nodeb_id; int a_rnc = a.rnc_id; int b_rnc = b.rnc_id; int a_msc = rnc[a_rnc].msc_id; int a_msc_2 = rnc[a_rnc].msc2_id; int b_msc = rnc[b_rnc].msc_id; int b_msc_2 = rnc[b_rnc].msc2_id; if(DISPLAY_ON_SCREEN == 1) { printf ( "Current node b no: %d is moving to %d \n" , a_nodeb , b_nodeb ); printf ("current rnc %d to %d \n" , a_rnc, b_rnc ); printf ("current msc %d to %d \n" , a_msc, b_msc ); printf ("current dualed msc %d to %d \n" ,a_msc_2 , b_msc_2 ); printf ("Reduced No of Complex handoff: %d" ,reduced_complex); } if(a_nodeb == b_nodeb) return 1; /* same nodeb */ else if(a_rnc == b_rnc) return 2; /* same rnc ||simplest */ else if(a_msc == b_msc) return 3; /* same msc || simple */ else if((b_msc_2 > 0) && (b_msc_2 == a_msc)) { reduced_complex++; alert(); return 3; } else

return 4;

/* diff msc || complex */

} /* ============================================================================================ void handoff_analysis(int type, int write_to_file = 0) This function determines the type of handooff performesd. Based on the second parameter it stores the result onto a file on the disk ============================================================================================ */ void handoff_analysis(int type, int write_to_file = 0) { static float _simplest = 0, simplest = 0, simple = 0, complex = 0; static long total_handoff = 0, totalhandoff_cost = 0; total_handoff++;

if(type == 1) _simplest++; else if(type == 2) simplest++; else if(type == 3) simple++; else if(type == 4) { complex++; /*alert()*/ } else { printf( "Invalid argument \n" ); exit(0); } totalhandoff_cost += type; /* calculating stats */ float _persimplest, persimplest, persimple, percomplex; _persimplest = (_simplest / total_handoff) * 100; persimplest = (simplest / total_handoff) * 100; persimple = (simple / total_handoff) * 100; percomplex = (complex / total_handoff) * 100; if(DISPLAY_ON_SCREEN == 1) { printf( printf( printf( printf( printf( printf( printf( printf( printf(

"Current Handoff cost : %d \n" , type ); "Cumulative total handoff cost: %d \n" , totalhandoff_cost ); "----------- S T A T I C T I C S ----------------- \n"); "Percentage of
} if(write_to_file == 1) { fstream hp; hp.open("analyis.txt", ios::out | ios::app); hp << _persimplest << " " << persimplest << " " << persimple << " " << percomplex << " " << filename << "\n"; hp.close(); } } /* ============================================================================================ create2darray() This functions implements the topology on the 2d matrix array. ============================================================================================ */ void create2darray() { printf("Enter the no of colums: "); cin >> nodebarray_col; printf( "Enter the no of rows: "); cin >> nodebarray_row; int currentnodeb_no = 1, i, j; nodebarray = (int **) calloc(sizeof(int), (nodebarray_row + 1)); for(i = 1; i <= nodebarray_row; i++) { nodebarray[i] = (int *) calloc(sizeof(int), (nodebarray_col + 1)); alocate memory */ for(j = 1; j <= nodebarray_col; j++) {

/*

nodebarray[i][j] = currentnodeb_no; currentnodeb_no++; } } /* populating the node b postions */ currentnodeb_no = 1; for(i = 1; i <= nodebarray_row; i++) { for(j = 1; j <= nodebarray_col; j++) { nodeb[currentnodeb_no].nodeb_x = i; nodeb[currentnodeb_no].nodeb_y = j; nodeb[currentnodeb_no].nodeb_id = currentnodeb_no; currentnodeb_no++; } } /* * displaying the array ; * for(i = 1; * i<=nodebarray_row ; * i++ ){ for(j=1; * j<=nodebarray_col ; * j++) cout<
nextmove[6][1] = y; nextmove[7][0] = x + 1; nextmove[7][1] = y + 1; srand((unsigned) clock()); RETRY: random_integer = (rand() % 7) + 1; nx = nextmove[random_integer][0]; ny = nextmove[random_integer][1]; if((nx <= 0) || (nx > nodebarray_row) || (ny <= 0) || (ny > nodebarray_col)) goto RETRY; /* boundary cond */ return; } /* ============================================================================================ FIXME: ============================================================================================ */ void randomwalk_nextpoint(int x, int y, int &nx, int &ny) { int newx, newy; int found = 0; while(!found) { randommove_randompos(x, y, newx, newy); found = ceil(is_neighbour(x, y, newx, newy)); } nx = newx; ny = newy; } /* ============================================================================================ void start_image() This function creates the image on which all movenents are recorded. ============================================================================================ */ void start_image() { int imgheight = 600; int imgwidth = 600; img = cvCreateImage(cvSize(imgheight, imgwidth), IPL_DEPTH_8U, 3); /* drawing the points */ int i, j, pointx, pointy; for(i = 1; i <= nodebarray_col; i++) { for(j = 1; j <= nodebarray_row; j++) { pointx = (imgwidth / (nodebarray_col + 1)) * i; pointy = (imgheight / (nodebarray_row + 1)) * j; cvCircle(img, cvPoint(pointx, pointy), 4, cvScalar(0, 255, 255), 1); } } } /* ============================================================================================ void draw_line(int col, int row, int x1, int y1, int x2, int y2) This function records the novents of the MS node on the matrix. ============================================================================================ */ void draw_line(int col, int row, int x1, int y1, int x2, int y2) { int width = img->width; int height = img->height;

int int int int

A B C D

= = = =

(width / (col + 1)) * x1; (height / (row + 1)) * y1; (width / (col + 1)) * x2; (height / (row + 1)) * y2;

cvLine ( img, cvPoint(A, B), cvPoint(C, D), cvScalar((rand() % 200 + 10), (rand() % 200 + 50), (rand() % 200 + 30)), 2 ); } /* ============================================================================================ void showimage(int a, int b, int c, int d, char winid[] = "") Displays the Recorded Image ============================================================================================ */ void showimage(int a, int b, int c, int d, char winid[] = "") { draw_line(nodebarray_col, nodebarray_row, a, b, c, d); if(DISPLAY_IMAGE == 1) { /* create a window */ char titlename[100]; strcpy(titlename, "simulation"); strcat(titlename, winid); cvNamedWindow(titlename, CV_WINDOW_AUTOSIZE); cvMoveWindow(titlename, 100, 100); /* move it to 100, 100 position */ cvShowImage(titlename, img); /* display the image */ cvWaitKey(10); } } /* ============================================================================================ void saveimage() Saves the Recorded image onto a file on the disk ============================================================================================ */ void saveimage() { time_t seconds = time(NULL); itoa(seconds, filename, 10); strcat(filename, ".jpg"); cvSaveImage(filename, img); } /* ============================================================================================ void random_walk(long steps = 0) This is the main function which does the random walk. ============================================================================================ */ void random_walk(long steps = 0) { srand((unsigned) clock()); int handoff_type; int snodeb, sx, sy; /* staring nodeb , x , y */ int nnodeb, nx, ny; /* next nodeb , x, y */ sx = (rand() % nodebarray_row) + 1; sy = (rand() % nodebarray_col) + 1; printf( "starting from %d,%d \n ", sx , sy ); long

loopcount = 0;

if(steps == 0) steps = 999; int lastcount; int wait_for; /* mobile res time */ while(loopcount < steps) { randomwalk_nextpoint(sx, sy, nx, ny); if(DISPLAY_ON_SCREEN == 1) printf( "moving to %d,%d \n ", nx, ny); snodeb = nodebarray[sx][sy]; nnodeb = nodebarray[nx][ny]; lastcount = (int) (loopcount / (steps - 1)); if(lastcount) saveimage(); handoff_analysis(handoff_cost(nodeb[snodeb], nodeb[nnodeb]), lastcount); showimage(sx, sy, nx, ny, PRGM_TID); sx = nx; sy = ny;

/* update present co-ordinates */

wait_for = rand() % 50; Sleep(wait_for); loopcount++; printf( "Loop Count: %l \n" , loopcount)

;

} } /* ============================================================================================ void main(int argc, char *argv[]) The Main Program ============================================================================================ */ void main(int argc, char *argv[]) { time_t t1, t2; t1 = time(NULL); if(argc >= 2) { PRGM_ID = atoi(argv[2]); strcpy(PRGM_TID, argv[2]); } ifstream

fp; /* initate a file pointer */

char fname[255]; printf( "File Name: "); gets(fname); fp.open(fname); if(!fp) { cerr << "Unable to open file"; exit(0); /* call system to stop */ } else { readfile(fp); create2darray(); start_image(); random_walk(TOT_HAND); fp.close(); } t2 = time(NULL); cout << " Program Running Time: " << (t2 - t1) << " Seconds" << endl; }

Study of Complex handoff in context of Simple and Dual Homing of ...

Study of Complex handoff in context of Simple and Dual Homing of RNC (Random Mobility Pattern).pdf. Study of Complex handoff in context of Simple and Dual ...

2MB Sizes 1 Downloads 122 Views

Recommend Documents

Axonal Propagation of Simple and Complex Spikes in ...
Jan 12, 2005 - parallel fibers (Thach, 1968; Gilbert and Thach, 1977; Kitazawa et .... and pCLAMP 8.2 software (Axon Instruments, Union City, CA). Data.

Simulation of DC dual-laterolog measurements in complex formations ...
primarily in vertical boreholes penetrating horizontal layers; only recently ... lengths of investigation while delivering measurements with high vertical resolution.

Complex Dynamics in a Simple Model of Signaling ...
Nov 15, 2007 - Each site receives k inputs. • Assign Boolean functions to each ... Dynamics. • All sites evolve according to its own rule. • 3 inputs: left. 3 inputs: ...

Simulation of Handoff Techniques in Mobile Cellular.pdf ...
average signal pattern due to scatters and different terrain variations as the mobile. moves. The slower fading effect (shadow fading) follow log-normal distribution. Hence handoff methods in the presence of multipath and shadow fading usually. resul

Dual luminescence of dimethylaminobenzaldehyde in ...
bond for commonly studied systems) which will be restricted in ... source. 3. Results and discussion. The absorption spectra of aqueous solutions of. DMABA as a .... the two factors open to be operative it is the polarity ... 01(1283)/93/EMR-. II).

Structure of cycles and local ordering in complex ...
Feb 17, 2004 - ranging from technological (the physical Internet) to social. (scientific ..... are collected and made publicly available by the National. Laboratory for ... of the World-Wide-Web domain collected at www.nd.edu. (c) Network of ...

Structure of cycles and local ordering in complex ...
Feb 17, 2004 - World-Wide-Web: Map of the World-Wide-Web col- lected at the domain of Notre Dame University2 [19–21]. This network is actually directed, ...

Herodotus-In-Context-Ethnography-Science-And-The-Art-Of ...
There was a problem previewing this document. Retrying... Download. Connect more apps... Try one of the apps below to open or edit this item. Herodotus-In-Context-Ethnography-Science-And-The-Art-Of-Persuasion.pdf. Herodotus-In-Context-Ethnography-Sci

Coevolution of Strategy and Structure in Complex ... - Semantic Scholar
Dec 19, 2006 - cumulative degree distributions exhibiting fast decaying tails [4] ... 1 (color online). .... associate the propensity to form new links and the lifetime.

Multiculturalism and education for citizenship in a context of ...
Multiculturalism and education for citizenship in a context of neoliberalism.pdf. Multiculturalism and education for citizenship in a context of neoliberalism.pdf.

in a Study-abroad Context
Asia Pacific Journal of Language in Education. (2000) Vol. 3, No. .... foreign language to satisfy part of a graduate degree requirement. In their I diary entries ...