Example

The queuing network is composed from two servers with FIFO queue of transactions waiting for a service. There are two sources of new transactions and two input points for them. There are also two output points - see the figure.

Queuing network with two serving nodes

We assume exponentially distributed random arrival time in input streams of transactions and exponentially distributed random service time of both servers. The corresponding parameters of the simulation model are then as follows:

lambda1
mean frequency of the first input stream (and the parameter of the exponential distribution of arrival time),
lambda2
mean frequency of the second input stream,
mu1
parameter of the exponential distribution of the first server service time (or the mean conditional frequency of services),
mu2
parameter of the exponential distribution of the second server service time.

Additional parameters are branching probabilities which describe passing of transactions through the network:

p1
probability of transaction departure (i.e. finishing) after being served in the node 1 (and with complementary value 1-p1 the transaction passes into the node 2),
p2
probability of transaction departure after being served in the node 2 (and with complementary value 1-p2 transaction passes into the node 1).

The output information of the model should be the response time Tq, i.e., the mean time which a transaction spends inside the network.

The construction of the model starts with object-oriented analysis of the problem. We will try to find types (i.e. classes in OOP terminology) of objects and their properties (i.e. attributes and/or methods). Moreover, we will follow the idea of reusability, so we will create more flexible types which can serve in a model of n-node network with m input streams as well. The found types are described in the subsequent items.

Transaction

We decided to use a "passive" model of the transaction (the "active" possibility means to take transaction as a process-like object). Due to the fact that we need to engage transaction in queues, we will derive type TRANSACTION from the supported LINK type. One more attribute of TRANSACTION is the time when transaction was generated. According to C-Sim syntax we have:

typedef struct {
  csim_d_link;
  double t_input;     /* "birth" time of transaction */
} TRANSACTION;

Queue

Our queue can be derived from the supported HEAD type which implements two-way circular list. The one more attribute of the QUEUE type is binding (i.e. pointer) to the object-server which is taking transactions out of the queue:

typedef struct {
  csim_d_head;
  PROCESS *server;  /* pointer to server */
} QUEUE;

Source

The source of transactions is evidently an "active" object which generates a Poisson stream of transactions. It means that type SOURCE must be derived from the supported type CSIM_PROCESS. We added attributes lambda-parameter of Poisson stream and binding to the queue where to put generated transactions:

typedef struct {
  csim_d_process;
  float lambda;  /* parameter of the pdf of interarrival time */
  QUEUE *queue;  /* pointer to output queue */
} SOURCE;

Type SOURCE describes local data record of an instance of the process. Moreover, we have to define a program of process' "life". Due to the fact that the program should be the same for all instances of source-like objects, it has to be constructed with property of reentrancy. We will show the example of C-Sim construction of such a program:

csim_program(SOURCE, SOURCE_PROG)
  TRANSACTION *p_poin; /* auxiliary pointer */
  for (;;) {
    p_poin = csim_new_link (TRANSACTION);
    p_poin->t_input = csim_time();
    into ((LINK *) p_poin, (HEAD *) my.queue );
    if (csim_idle (my.queue->server))
      csim_activate_at (my.queue->server, csim_time());
    csim_hold(csim_negexp(my.lambda));
  }
csim_end_program

Server

The last (and the most complex) type we need is SERVER. This type describes data of a server-like object. Server introduces evidently an "activity", so we derived its data type from the CSIM_PROCESS. The meaning of added attributes is explained in comments. We have only to note that with regard to the intended (almost) universal utilization of server objects it is convenient "to distribute" a capability to gather statistical data across all server objects (i.e. a server gathers statistic of transactions which are completely finished after the service).

typedef struct {
  csim_d_process;
  float mi;          /* rate of service, exponential pdf */
  float p;           /* prob. of departure after the service */
  QUEUE *in_queue;   /* pointer to an input queue */
  QUEUE *out_queue;  /* pointer to an output queue */
  UWORD cnt;         /* counter of serviced transactions */
  double stq;        /* sum of responses of finished transactions */
} SERVER;

The complete program for server processes can be found in source file oqn.c.

In order to create and set up all the model of queuing network we have to: