Exemplo n.º 1
0
static glbsp_ret_e HandleLevel(void)
{
  superblock_t *seg_list;
  node_t *root_node;
  node_t *root_stale_node;
  subsec_t *root_sub;

  glbsp_ret_e ret;

  if (cur_comms->cancelled)
    return GLBSP_E_Cancelled;

  DisplaySetBarLimit(1, 1000);
  DisplaySetBar(1, 0);

  cur_comms->build_pos = 0;

  LoadLevel();

  InitBlockmap();

  // create initial segs
  seg_list = CreateSegs();

  root_stale_node = (num_stale_nodes == 0) ? NULL : 
      LookupStaleNode(num_stale_nodes - 1);

  // recursively create nodes
  ret = BuildNodes(seg_list, &root_node, &root_sub, 0, root_stale_node);
  FreeSuper(seg_list);

  if (ret == GLBSP_E_OK)
  {
    ClockwiseBspTree(root_node);

    PrintVerbose("Built %d NODES, %d SSECTORS, %d SEGS, %d VERTEXES\n",
        num_nodes, num_subsecs, num_segs, num_normal_vert + num_gl_vert);

    if (root_node)
      PrintVerbose("Heights of left and right subtrees = (%d,%d)\n",
          ComputeBspHeight(root_node->r.node),
          ComputeBspHeight(root_node->l.node));

    SaveLevel(root_node);
  }

  FreeLevel();
  FreeQuickAllocCuts();
  FreeQuickAllocSupers();

  return ret;
}
Exemplo n.º 2
0
void PruneSidedefs(void)
{
  int i;
  int new_num;
  int unused = 0;

  DisplayTicker();

  // scan all sidedefs
  for (i=0, new_num=0; i < num_sidedefs; i++)
  {
    sidedef_t *S = lev_sidedefs[i];

    if (S->ref_count < 0)
      InternalError("Sidedef %d ref_count is %d", i, S->ref_count);
    
    if (S->ref_count == 0)
    {
      if (S->sector)
        S->sector->ref_count--;

      if (S->equiv == NULL)
        unused++;

      UtilFree(S);
      continue;
    }

    S->index = new_num;
    lev_sidedefs[new_num++] = S;
  }

  if (new_num < num_sidedefs)
  {
    int dup_num = num_sidedefs - new_num - unused;

    if (unused > 0)
      PrintVerbose("Pruned %d unused sidedefs\n", unused);

    if (dup_num > 0)
      PrintVerbose("Pruned %d duplicate sidedefs\n", dup_num);

    num_sidedefs = new_num;
  }

  if (new_num == 0)
    FatalError("Couldn't find any Sidedefs");
}
Exemplo n.º 3
0
void PruneVertices(void)
{
  int i;
  int new_num;
  int unused = 0;

  DisplayTicker();

  // scan all vertices
  for (i=0, new_num=0; i < num_vertices; i++)
  {
    vertex_t *V = lev_vertices[i];

    if (V->ref_count < 0)
      InternalError("Vertex %d ref_count is %d", i, V->ref_count);
    
    if (V->ref_count == 0)
    {
      if (V->equiv == NULL)
        unused++;

      UtilFree(V);
      continue;
    }

    V->index = new_num;
    lev_vertices[new_num++] = V;
  }

  if (new_num < num_vertices)
  {
    int dup_num = num_vertices - new_num - unused;

    if (unused > 0)
      PrintVerbose("Pruned %d unused vertices "
        "(this is normal if the nodes were built before)\n", unused);

    if (dup_num > 0)
      PrintVerbose("Pruned %d duplicate vertices\n", dup_num);

    num_vertices = new_num;
  }

  if (new_num == 0)
    FatalError("Couldn't find any Vertices");
 
  num_normal_vert = num_vertices;
}
void UAblSetShaderParameterTask::InternalSetShaderValue(UMaterialInstanceDynamic* DynMaterial, UAblSetParameterValue* Value, UAblSetParameterValue* PreviousValue, float BlendAlpha) const
{
	check(DynMaterial);
	check(Value);
	check(PreviousValue);

#if !(UE_BUILD_SHIPPING)
	if (IsVerbose())
	{
		PrintVerbose(FString::Printf(TEXT("Setting material parameter %s on Material %s to %s with a blend of %1.4f."), *m_ParameterName.ToString(), *DynMaterial->GetName(), *Value->ToString(), BlendAlpha));
	}
#endif

	if (UAblSetScalarParameterValue* ScalarValue = Cast<UAblSetScalarParameterValue>(Value))
	{
		UAblSetScalarParameterValue* PreviousScalarValue = CastChecked<UAblSetScalarParameterValue>(PreviousValue);
		float InterpolatedValue = FMath::Lerp(PreviousScalarValue->GetScalar(), ScalarValue->GetScalar(), BlendAlpha);
		DynMaterial->SetScalarParameterValue(m_ParameterName, InterpolatedValue);
	}
	else if (UAblSetVectorParameterValue* VectorValue = Cast<UAblSetVectorParameterValue>(Value))
	{
		UAblSetVectorParameterValue* PreviousVectorValue = CastChecked<UAblSetVectorParameterValue>(PreviousValue);
		FVector InterpolatedValue = FMath::Lerp(PreviousVectorValue->GetVector(), VectorValue->GetVector(), BlendAlpha);
		DynMaterial->SetVectorParameterValue(m_ParameterName, InterpolatedValue);
	}
	else if (UAblSetTextureParameterValue* TextureValue = Cast<UAblSetTextureParameterValue>(Value))
	{
		// No Lerping allowed.
		DynMaterial->SetTextureParameterValue(m_ParameterName, TextureValue->GetTexture());
	}
	else
	{
		checkNoEntry();
	}
}
Exemplo n.º 5
0
void PruneSectors(void)
{
  int i;
  int new_num;

  DisplayTicker();

  // scan all sectors
  for (i=0, new_num=0; i < num_sectors; i++)
  {
    sector_t *S = lev_sectors[i];

    if (S->ref_count < 0)
      InternalError("Sector %d ref_count is %d", i, S->ref_count);
    
    if (S->ref_count == 0)
    {
      UtilFree(S);
      continue;
    }

    S->index = new_num;
    lev_sectors[new_num++] = S;
  }

  if (new_num < num_sectors)
  {
    PrintVerbose("Pruned %d unused sectors\n", num_sectors - new_num);
    num_sectors = new_num;
  }

  if (new_num == 0)
    FatalError("Couldn't find any Sectors");
}
Exemplo n.º 6
0
Arquivo: wad.c Projeto: samboy/Oblige
//
// ReadWadFile
//
glbsp_ret_e ReadWadFile(const char *filename)
{
  int check;
  char *read_msg;

  // open input wad file & read header
  in_file = fopen(filename, "rb");

  if (! in_file)
  {
    if (errno == ENOENT)
      SetErrorMsg("Cannot open WAD file: %s", filename); 
    else
      SetErrorMsg("Cannot open WAD file: %s [%s]", filename, 
          strerror(errno));

    return GLBSP_E_ReadError;
  }
  
  if (! ReadHeader(filename))
  {
    fclose(in_file);
    return GLBSP_E_ReadError;
  }

  PrintMsg("Opened %cWAD file : %s\n", (wad.kind == IWAD) ? 'I' : 'P', 
      filename); 
  PrintVerbose("Reading %d dir entries at 0x%X\n", wad.num_entries, 
      wad.dir_start);

  // read directory
  ReadDirectory();

  DisplayOpen(DIS_FILEPROGRESS);
  DisplaySetTitle("glBSP Reading Wad");
  
  read_msg = UtilFormat("Reading: %s", filename);

  DisplaySetBarText(1, read_msg);
  DisplaySetBarLimit(1, CountLumpTypes(LUMP_READ_ME, LUMP_READ_ME));
  DisplaySetBar(1, 0);

  UtilFree(read_msg);

  cur_comms->file_pos = 0;

  // now read lumps
  check = ReadAllLumps();

  if (check != wad.num_entries)
    InternalError("Read directory count consistency failure (%d,%d)",
      check, wad.num_entries);
  
  wad.current_level = NULL;

  DisplayClose();

  return GLBSP_E_OK;
}
Exemplo n.º 7
0
//
// PutReject
//
// For now we only do very basic reject processing, limited to
// determining all isolated groups of sectors (islands that are
// surrounded by void space).
//
void PutReject(void)
{
  CreateLevelLump("REJECT");

//  AppendLevelLump(lump, matrix, reject_size);

  PrintVerbose("Added empty reject lump\n");
}
Exemplo n.º 8
0
Arquivo: df.cpp Projeto: DonCN/haiku
int
main(int argc, char **argv)
{
	char *programName = argv[0];
	if (strrchr(programName, '/'))
		programName = strrchr(programName, '/') + 1;

	bool showBlocks = false;
	bool all = false;
	dev_t device = -1;

	while (*++argv) {
		char *arg = *argv;
		if (*arg == '-') {
			while (*++arg && isalpha(*arg)) {
				switch (arg[0]) {
					case 'a':
						all = true;
						break;
					case 'b':
						showBlocks = true;
						break;
					default:
						ShowUsage(programName);
				}
			}
			if (arg[0] == '-') {
				arg++;
				if (!strcmp(arg, "all"))
					all = true;
				else if (!strcmp(arg, "blocks"))
					showBlocks = true;
				else
					ShowUsage(programName);
			}
		} else
			break;
	}

	// Do we already have a device? Then let's print out detailed info about that

	if (argv[0] != NULL) {
		PrintVerbose(dev_for_path(argv[0]));
		return 0;
	}

	// If not, then just iterate over all devices and give a compact summary

	printf("Mount           Type      Total     Free     Flags   Device\n"
		"--------------- -------- --------- --------- ------- --------------------------\n");

	int32 cookie = 0;
	while ((device = next_dev(&cookie)) >= B_OK) {
		PrintCompact(device, showBlocks, all);
	}

	return 0;
}
// The first message of a file transfer is a discovery request byt the client. This function handles such requests.
HRESULT CFileRepServer::SendFileInfo(
    __in CRequest* request, 
    __in_z const LPWSTR fileName, 
    __in LONGLONG fileLength, 
    __in DWORD chunkSize)
{
    PrintVerbose(L"Entering CFileRepServer::SendFileInfo");

    HRESULT hr = S_OK;
    WS_ERROR* error = request->GetError();
    WS_MESSAGE* replyMessage = request->GetReplyMessage();
    WS_MESSAGE* requestMessage = request->GetRequestMessage();
    WS_CHANNEL* channel = request->GetChannel();

    FileInfo fileInfo;
    fileInfo.fileName = fileName;
    fileInfo.fileLength = fileLength;
    fileInfo.chunkSize = chunkSize;

    WS_MESSAGE_DESCRIPTION fileInfoMessageDescription;
    fileInfoMessageDescription.action = &fileInfoAction;
    fileInfoMessageDescription.bodyElementDescription = &fileInfoElement;

    hr = WsSendReplyMessage(
        channel,
        replyMessage,
        &fileInfoMessageDescription,
        WS_WRITE_REQUIRED_VALUE,
        &fileInfo,
        sizeof(fileInfo),
        requestMessage,
        NULL,
        error);

    if (FAILED(hr))
    {
        PrintError(L"CFileRepServer::SendFileInfo", true);
        PrintError(hr, error, true);
    }

    WsResetMessage(replyMessage, NULL);

    PrintVerbose(L"Leaving CFileRepServer::SendFileInfo");
    return hr;
}
// The server version of ProcessMessage. This is the entry point for the application-specific code.
HRESULT CFileRepServer::ProcessMessage(
    __in CRequest* request,
    __in const WS_XML_STRING* receivedAction)
{
    PrintVerbose(L"Entering CFileRepServer::ProcessMessage");

    HRESULT hr = S_OK;
    FileRequest* fileRequest = NULL;
    WS_MESSAGE* requestMessage = request->GetRequestMessage();
    WS_CHANNEL* channel = request->GetChannel();
    WS_ERROR* error = request->GetError();

    // Make sure action is what we expect
    if (WsXmlStringEquals(receivedAction, &fileRequestAction, error) != S_OK)
    {
        PrintInfo(L"Illegal action");

        hr = WS_E_ENDPOINT_ACTION_NOT_SUPPORTED;
    }
    else
    {
        // Read file request

        WS_HEAP* heap;
        IfFailedExit(WsGetMessageProperty(requestMessage, WS_MESSAGE_PROPERTY_HEAP, &heap, sizeof(heap), error));

        IfFailedExit(WsReadBody(requestMessage, &fileRequestElement, WS_READ_REQUIRED_POINTER,
            heap, &fileRequest, sizeof(fileRequest), error));
        IfFailedExit(WsReadMessageEnd(channel, requestMessage, NULL, error));

        IfFailedExit(ReadAndSendFile(request, fileRequest->fileName, fileRequest->filePosition, error));
    }

    EXIT

    // We do not print error messages here. That is handled in the caller.
    PrintVerbose(L"Leaving CFileRepServer::ProcessMessage");
    return hr;
}
Exemplo n.º 11
0
void DetectOverlappingLines(void)
{
  // Algorithm:
  //   Sort all lines by left-most vertex.
  //   Overlapping lines will then be near each other in this set.
  //   Note: does not detect partially overlapping lines.

  int i;
  int *array = UtilCalloc(num_linedefs * sizeof(int));
  int count = 0;

  DisplayTicker();

  // sort array of indices
  for (i=0; i < num_linedefs; i++)
    array[i] = i;
  
  qsort(array, num_linedefs, sizeof(int), LineStartCompare);

  for (i=0; i < num_linedefs - 1; i++)
  {
    int j;

    for (j = i+1; j < num_linedefs; j++)
    {
      if (LineStartCompare(array + i, array + j) != 0)
        break;

      if (LineEndCompare(array + i, array + j) == 0)
      {
        linedef_t *A = lev_linedefs[array[i]];
        linedef_t *B = lev_linedefs[array[j]];

        // found an overlap !
        B->overlap = A->overlap ? A->overlap : A;

        count++;
      }
    }
  }

  if (count > 0)
  {
      PrintVerbose("Detected %d overlapped linedefs\n", count);
  }

  UtilFree(array);
}
void UAblSetCollisionChannelResponseTask::OnTaskEnd(const TWeakObjectPtr<const UAblAbilityContext>& Context, const EAblAbilityTaskResult result) const
{
	Super::OnTaskEnd(Context, result);

	if (m_RestoreOnEnd)
	{
		UAblSetCollisionChannelResponseTaskScratchPad* ScratchPad = Cast<UAblSetCollisionChannelResponseTaskScratchPad>(Context->GetScratchPadForTask(this));
		check(ScratchPad);

		for (const FCollisionLayerResponseEntry& Entry : ScratchPad->PreviousCollisionValues)
		{
			if (Entry.Primitive.IsValid())
			{
#if !(UE_BUILD_SHIPPING)
				if (IsVerbose())
				{
					PrintVerbose(FString::Printf(TEXT("Setting Collision Channel %s Response on Actor %s to %s."), *FAbleLogHelper::GetCollisionChannelEnumAsString(Entry.Channel), *Entry.Primitive->GetOwner()->GetName(), *FAbleLogHelper::GetCollisionResponseEnumAsString(Entry.Response)));
				}
#endif
				Entry.Primitive->SetCollisionResponseToChannel(Entry.Channel, Entry.Response);
			}
		}
	}
}
Exemplo n.º 13
0
glbsp_ret_e GlbspBuildNodes(const nodebuildinfo_t *info,
    const nodebuildfuncs_t *funcs, volatile nodebuildcomms_t *comms)
{
  char *file_msg;

  glbsp_ret_e ret = GLBSP_E_OK;

  cur_info  = info;
  cur_funcs = funcs;
  cur_comms = comms;

  cur_comms->total_big_warn = 0;
  cur_comms->total_small_warn = 0;

  // clear cancelled flag
  comms->cancelled = FALSE;

  // sanity check
  if (!cur_info->input_file  || cur_info->input_file[0] == 0 ||
      !cur_info->output_file || cur_info->output_file[0] == 0)
  {
    SetErrorMsg("INTERNAL ERROR: Missing in/out filename !");
    return GLBSP_E_BadArgs;
  }

  InitDebug();
  InitEndian();
 
  if (info->missing_output)
    PrintMsg("* No output file specified. Using: %s\n\n", info->output_file);

  if (info->same_filenames)
    PrintMsg("* Output file is same as input file. Using -loadall\n\n");

  // opens and reads directory from the input wad
  ret = ReadWadFile(cur_info->input_file);

  if (ret != GLBSP_E_OK)
  {
    TermDebug();
    return ret;
  }

  if (CountLevels() <= 0)
  {
    CloseWads();
    TermDebug();

    SetErrorMsg("No levels found in wad !");
    return GLBSP_E_Unknown;
  }
   
  PrintMsg("\n");
  PrintVerbose("Creating nodes using tunable factor of %d\n", info->factor);

  DisplayOpen(DIS_BUILDPROGRESS);
  DisplaySetTitle("glBSP Build Progress");

  file_msg = UtilFormat("File: %s", cur_info->input_file);
 
  DisplaySetBarText(2, file_msg);
  DisplaySetBarLimit(2, CountLevels() * 10);
  DisplaySetBar(2, 0);

  UtilFree(file_msg);
  
  cur_comms->file_pos = 0;
  
  // loop over each level in the wad
  while (FindNextLevel())
  {
    ret = HandleLevel();

    if (ret != GLBSP_E_OK)
      break;

    cur_comms->file_pos += 10;
    DisplaySetBar(2, cur_comms->file_pos);
  }

  DisplayClose();

  // writes all the lumps to the output wad
  if (ret == GLBSP_E_OK)
  {
    ret = WriteWadFile(cur_info->output_file);

    // when modifying the original wad, any GWA companion must be deleted
    if (ret == GLBSP_E_OK && cur_info->same_filenames)
      DeleteGwaFile(cur_info->output_file);

    PrintMsg("\n");
    PrintMsg("Total serious warnings: %d\n", cur_comms->total_big_warn);
    PrintMsg("Total minor warnings: %d\n", cur_comms->total_small_warn);

    ReportFailedLevels();
  }

  // close wads and free memory
  CloseWads();

  TermDebug();

  cur_info  = NULL;
  cur_comms = NULL;
  cur_funcs = NULL;

  return ret;
}
void UAblRayCastQueryTask::OnTaskStart(const TWeakObjectPtr<const UAblAbilityContext>& Context) const
{
	Super::OnTaskStart(Context);

	AActor* SourceActor = m_QueryLocation.GetSourceActor(*Context.Get());
	check(SourceActor);

	UWorld* World = SourceActor->GetWorld();

	FTransform QueryTransform;
	m_QueryLocation.GetTransform(*Context.Get(), QueryTransform);

	const FVector RayStart = QueryTransform.GetLocation();
	const FVector RayEnd = RayStart + QueryTransform.GetRotation().GetForwardVector() * m_Length;

	if (m_UseAsyncQuery && UAbleSettings::IsAsyncEnabled())
	{
		UAblRayCastQueryTaskScratchPad* ScratchPad = Cast<UAblRayCastQueryTaskScratchPad>(Context->GetScratchPadForTask(this));
		check(ScratchPad);
		if (m_OnlyReturnBlockingHit)
		{
			ScratchPad->AsyncHandle = World->AsyncLineTraceByChannel(EAsyncTraceType::Single, RayStart, RayEnd, m_CollisionChannel);
		}
		else
		{
			ScratchPad->AsyncHandle = World->AsyncLineTraceByChannel(EAsyncTraceType::Multi, RayStart, RayEnd, m_CollisionChannel);
		}
	}
	else
	{
		TArray<FHitResult> HitResults;
		FHitResult TraceResult;
		if (m_OnlyReturnBlockingHit)
		{
			if (World->LineTraceSingleByChannel(TraceResult, RayStart, RayEnd, m_CollisionChannel))
			{
				HitResults.Add(TraceResult);
			}
		}
		else
		{
			World->LineTraceMultiByChannel(HitResults, RayStart, RayEnd, m_CollisionChannel);		
		}

#if !(UE_BUILD_SHIPPING)
		if (IsVerbose())
		{
			PrintVerbose(FString::Printf(TEXT("Raycast found %d results."), HitResults.Num()));
		}
#endif

		if (HitResults.Num())
		{
#if !(UE_BUILD_SHIPPING)
			if (IsVerbose())
			{
				// Quick distance print help to see if we hit ourselves.
				float DistanceToBlocker = HitResults[HitResults.Num() - 1].Distance;
				PrintVerbose(FString::Printf(TEXT("Raycast blocking hit distance: %4.2f."), DistanceToBlocker));
			}
#endif

			if (m_CopyResultsToContext)
			{
#if !(UE_BUILD_SHIPPING)
				if (IsVerbose())
				{
					PrintVerbose(FString::Printf(TEXT("Copying %d results into Context."), HitResults.Num()));
				}
#endif
				CopyResultsToContext(HitResults, Context);
			}

			if (m_FireEvent)
			{
#if !(UE_BUILD_SHIPPING)
				if (IsVerbose())
				{
					PrintVerbose(FString::Printf(TEXT("Firing Raycast Event %s with %d results."), *m_Name.ToString(), HitResults.Num()));
				}
#endif
				Context->GetAbility()->OnRaycastEvent(Context.Get(), m_Name, HitResults);
			}
		}
	}

#if !UE_BUILD_SHIPPING
	if (FAblAbilityDebug::ShouldDrawQueries())
	{
		FAblAbilityDebug::DrawRaycastQuery(World, QueryTransform, m_Length);
	}
#endif
}
void UAblSetCollisionChannelResponseTask::OnTaskStart(const TWeakObjectPtr<const UAblAbilityContext>& Context) const
{
	Super::OnTaskStart(Context);

	UAblSetCollisionChannelResponseTaskScratchPad* ScratchPad = nullptr;
	
	if (m_RestoreOnEnd)
	{
		ScratchPad = Cast<UAblSetCollisionChannelResponseTaskScratchPad>(Context->GetScratchPadForTask(this));
		check(ScratchPad);
	}

	// We need to convert our Actors to primitive components.
	TArray<TWeakObjectPtr<AActor>> TargetArray;
	GetActorsForTask(Context, TargetArray);

	TArray<TWeakObjectPtr<UPrimitiveComponent>> PrimitiveComponents;

	for (TWeakObjectPtr<AActor>& Target : TargetArray)
	{
		if (UPrimitiveComponent* PrimitiveComponent = Cast<UPrimitiveComponent>(Target->GetRootComponent()))
		{
			PrimitiveComponents.AddUnique(PrimitiveComponent);
		}
	}

	for (TWeakObjectPtr<UPrimitiveComponent>& Component : PrimitiveComponents)
	{
		if (Component.IsValid())
		{
			if (m_RestoreOnEnd)
			{
				if (m_SetAllChannelsToResponse)
				{
					const FCollisionResponseContainer& Container = Component->GetCollisionResponseToChannels();
					for (ECollisionChannel Channel : TEnumRange<ECollisionChannel>())
					{
						ScratchPad->PreviousCollisionValues.Add(FCollisionLayerResponseEntry(Component.Get(), Channel, Container.GetResponse(Channel)));
					}
				}
				else
				{
					ScratchPad->PreviousCollisionValues.Add(FCollisionLayerResponseEntry(Component.Get(), m_Channel.GetValue(), Component->GetCollisionResponseToChannel(m_Channel)));
				}
			}

			if (m_SetAllChannelsToResponse)
			{
#if !(UE_BUILD_SHIPPING)
				if (IsVerbose())
				{
					PrintVerbose(FString::Printf(TEXT("Setting All Collision Responses on Actor %s to %s."), *Component->GetOwner()->GetName(), *FAbleLogHelper::GetCollisionResponseEnumAsString(m_Response.GetValue())));
				}
#endif
				Component->SetCollisionResponseToAllChannels(m_Response.GetValue());
			}
			else
			{
#if !(UE_BUILD_SHIPPING)
				if (IsVerbose())
				{
					PrintVerbose(FString::Printf(TEXT("Setting Collision Channel %s Response on Actor %s to %s."), *FAbleLogHelper::GetCollisionChannelEnumAsString(m_Channel.GetValue()), *Component->GetOwner()->GetName(), *FAbleLogHelper::GetCollisionResponseEnumAsString(m_Response.GetValue())));
				}
#endif
				Component->SetCollisionResponseToChannel(m_Channel.GetValue(), m_Response.GetValue());
			}
		}
	}
}
Exemplo n.º 16
0
Arquivo: ihm10.c Projeto: geoxuan/PIHM
/* Main Function */
int main(int argc, char *argv[])
{  
  char *filename = "shalehills";        /* Input file name prefix    */
  char *StateFile;                /* Output file name string   */
  char *FluxFile;
  char *ETISFile;  
  char *QFile;  
  
  Model_Data mData;               /* Model Data                */
  Control_Data cData;             /* Solver Control Data       */
  
  N_Vector CV_Y;                  /* State Variables Vector    */
  M_Env machEnv;                  /* Machine Environments      */
  
  realtype ropt[OPT_SIZE];        /* Optional real type and integer type  */
  long int iopt[OPT_SIZE];        /* vecter for Message Passing to solver */
  
  void *cvode_mem;                /* Model Data Pointer        */
  int flag;                       /* flag to test return value */
  
  FILE *res_state_file;           /* Output file for States    */
  FILE *res_flux_file;            /* Output file for Flux      */
  FILE *res_etis_file;            /* Output file for ET and IS */
  FILE *res_q_file;
  
  int N;                          /* Problem size              */
  int i;                          /* loop index                */
  realtype t;                     /* simulation time           */
  realtype NextPtr, StepSize;     /* stress period & step size */
  
  clock_t start, end_r, end_s;    /* system clock at points    */
  realtype cputime_r, cputime_s;  /* for duration in realtype  */
  
  /* allocate memory for model data structure */
  mData = (Model_Data)malloc(sizeof *mData);
  start = clock();
  
  /* get user specified file name in command line */
  if(argc >= 2)
  {
    filename = (char *)malloc(strlen(argv[1])*sizeof(char));
    strcpy(filename, argv[1]);
  }  
  
  printf("\nBelt up!  PIHM 1.0 is starting ... \n");
  
  /* read in 7 input files with "filename" as prefix */
  read_alloc(filename, mData, &cData); 
    
  /* problem size */
  N = 3*mData->NumEle + mData->NumRiv;
  
  /* initial machine environment variable */
  machEnv = M_EnvInit_Serial(N);
  
  /* initial state variable depending on machine*/
  CV_Y = N_VNew(N, machEnv);
  
  /* initialize mode data structure */
  initialize(filename, mData, &cData, CV_Y);
  
  if(cData.Debug == 1) {PrintModelData(mData);}  
  
  end_r = clock();
  cputime_r = (end_r - start)/(realtype)CLOCKS_PER_SEC;
  
  printf("\nSolving ODE system ... \n");
  
  /* initial control parameter for CVODE solver. Otherwise the default value by C could cause problems. */
  for(i=0; i<OPT_SIZE; i++)
  {
    ropt[i] = 0.0;
    iopt[i] = 0;
  }
  
  /* set user specified control parameter */
  ropt[H0] = cData.InitStep;  
  ropt[HMAX] = cData.MaxStep; 
  
  /* allocate memory for solver */
  cvode_mem = CVodeMalloc(N, f, cData.StartTime, CV_Y, BDF, NEWTON, SS, &cData.reltol, 
                          &cData.abstol, mData, NULL, TRUE, iopt, ropt, machEnv);
  if(cvode_mem == NULL) {printf("CVodeMalloc failed. \n"); return(1);}
  
  if(cData.Solver == 1)
  {
    /* using dense direct solver */
    flag = CVDense(cvode_mem, NULL, NULL);
    if(flag != SUCCESS) {printf("CVDense failed. \n"); return(1);}
  } 
  else if(cData.Solver == 2)
  {
    /* using iterative solver */
    flag = CVSpgmr(cvode_mem, NONE, cData.GSType, cData.MaxK, cData.delt, NULL, NULL,
                       mData, NULL, NULL);
    if (flag != SUCCESS) {printf("CVSpgmr failed."); return(1);}
  } 
  
  /*allocate and copy to get output file name */
  StateFile = (char *)malloc((strlen(filename)+4)*sizeof(char));
  strcpy(StateFile, filename);
  FluxFile  = (char *)malloc((strlen(filename)+5)*sizeof(char));
  strcpy(FluxFile, filename);
  ETISFile  = (char *)malloc((strlen(filename)+5)*sizeof(char));
  strcpy(ETISFile, filename);
  QFile = (char *)malloc((strlen(filename)+2)*sizeof(char));
  strcpy(QFile, filename);
  
  /* open output file */
  if (cData.res_out == 1) {res_state_file = fopen(strcat(StateFile, ".res"), "w");}
  if (cData.flux_out == 1) {res_flux_file = fopen(strcat(FluxFile, ".flux"), "w");}
  if (cData.etis_out == 1) {res_etis_file = fopen(strcat(ETISFile, ".etis"), "w");}
  if (cData.q_out == 1) {res_q_file = fopen(strcat(QFile, ".q"), "w");}
  
  /* print header of output file */
  if (cData.res_out == 1) {FPrintYheader(res_state_file, mData);}
  if (cData.etis_out == 1) {FPrintETISheader(res_etis_file, mData);}
  if (cData.q_out == 1) {FPrintETISheader(res_q_file, mData);}
  printf("\n");
  
  /* set start time */
  t = cData.StartTime;
  
  /* start solver in loops */
  for(i=0; i<cData.NumSteps; i++)
  {
    /* prompt information in non-verbose mode */
    if (cData.Verbose != 1)
    {
      printf("  Running: %-4.1f%% ... ", (100*(i+1)/((realtype) cData.NumSteps))); 
      fflush(stdout);
    }
    
    /* inner loops to next output points with ET step size control */
    while(t < cData.Tout[i+1])
    {
      if (t + cData.ETStep >= cData.Tout[i+1])
      {
        NextPtr = cData.Tout[i+1];
      }
      else
      {
        NextPtr = t + cData.ETStep;
      }
      StepSize = NextPtr - t; 
      
      /* calculate Interception Storage */
      calIS(t, StepSize, mData);
      /* solving ODE system */
      flag = CVode(cvode_mem, NextPtr, CV_Y, &t, NORMAL);  
      /* calculate ET and adjust states variables*/
      calET(t, StepSize, CV_Y, mData);
    }  
    
    if(cData.Verbose == 1) {PrintVerbose(i, t, iopt, ropt);}

    /* uncomment it if user need it verbose mode */  
    /* if(cData.Verbose == 1) {PrintY(mData, CV_Y, t);} */
    
    /* print out results to files at every output time */
    if (cData.res_out == 1) {FPrintY(mData, CV_Y, t, res_state_file);}
    if (cData.flux_out == 1) {FPrintFlux(mData, t, res_flux_file);}
    if (cData.etis_out == 1) {FPrintETIS(mData, t, res_etis_file);}
    if (cData.q_out == 1) {FPrintQ(mData, t, res_q_file);}
    
    if (cData.Verbose != 1) {printf("\r");}  
    
    if(flag != SUCCESS) {printf("CVode failed, flag = %d. \n", flag); return(flag);} 
    
    /* clear buffer */
    fflush(stdout);  
  }
  
  /* free memory */
  /*
  N_VFree(CV_Y);
  CVodeFree(cvode_mem);
  M_EnvFree_Serial(machEnv); 
  */
  
  /* capture time */
  end_s = clock();
  cputime_s = (end_s - end_r)/(realtype)CLOCKS_PER_SEC;
  
  /* print out simulation statistics */
  PrintFarewell(cData, iopt, ropt, cputime_r, cputime_s);
  if (cData.res_out == 1) {FPrintFarewell(cData, res_state_file, iopt, ropt, cputime_r, cputime_s);}
  
  /* close output files */
  if (cData.res_out == 1)  {fclose(res_state_file);}
  if (cData.flux_out == 1) {fclose(res_flux_file);}
  if (cData.etis_out == 1) {fclose(res_etis_file);}
  if (cData.q_out == 1)    {fclose(res_q_file);}
  
  free(mData);
  
  return 0;
}
Exemplo n.º 17
0
int main(int argc, char **argv){
  long   j, p;
  int    pos, last, flushpos;
#ifdef __LUNA_DEBUG
  clock_t start, end; 
#endif
  struct Dhash* DHash;
  struct mallinfo MI;
  struct list * liste;
  DNAhash  hashliste;

#ifdef __LUNA_DEBUG
  start = clock();
#endif

  CommandLine(argc, argv);

  // reading the sequence from stdin. 
  p =  0; 
  f1 = FastaIn();
  f2 = FastaIn();

  hashliste = MakeDNAhash(klgde);

  if (SeqLgth > 100000)
    flushpos = 10000;
  else
    flushpos = SeqLgth / 100;
  if (flushpos<100)
    flushpos = 100;

  printf("%s : Sequence length : %-7ld   Tuble : %2d Gap: %2d",
	 ProgramName, p, klgde, gap - klgde);

  if (Insert)
    printf("  Insert : %d", Insert);

  printf("\nComparing sequences : \n\t%s (%d)\n\t%s (%d)\n", 
	 f1->navn, 
	 f1->length,
	 f2->navn,
	 f2->length);

  // find the longest string ...
  //p = (f1->length>f2->length) ? f1->length : f2->length;
  p = f1->length;

  DHash = MakeDHash(p);
  last = 0;

  DistMin = 0;
  if (verbose)
    fprintf(stderr, "Building k-probe database\n");
  for (j = 0; j < p - klgde; j+=klgde - back) {    
    liste = 0;
    pos = FetchDNA(&f1->seq[j]);
    if (pos == -1)
      continue;
    hashliste[pos] = insertNode(hashliste[pos]);
    hashliste[pos]->start = j;
    if (verbose)
      if ((!(j % 1)) &&
	  ((j * 100 / p) != last)) {
	last = (j * 100 /p);
	fprintf(stderr, "\rBuilding : %d %%",  last);
	fflush(stderr);
      }
  }
  if (verbose)
    fprintf(stderr, "\rBuilding : 100 %% .... Done\n");

  //Sammen ligningen del 2.
  //p = (f1->length>f2->length) ? f1->length : f2->length; //f2->length;
  p = f2->length;
  if (p > 100000)
    flushpos = 10000;
  else
    flushpos = p / 100;

  if (verbose) 
    fprintf(stderr, "Finding inverted repeats\n");

  for (j = 0; j < p - klgde; j+=klgde - back) {    
    liste = 0;
    pos = FetchDNA(&f2->seq[j]);
    if (pos == -1)
      continue;
    liste = hashliste[pos];
    HashCalcDistGar(DHash, liste, j);

    // Let me show you my hash signs while I work
    if (!(j % flushpos)) {
      last = (j * 100 / p);
      if (verbose)
	fprintf(stderr, "\rProgress : %d %%",  last);
      DHashFlush(DHash, j);
    }
  }
  if (verbose)
    fprintf(stderr, "\rProgress : 100 %%\n");
  DHashLastFlush(DHash);

  printf("\n\n");
  
  // So You wanna know the time and memory usage well... verbose we are.
  if (verbose) {
    PrintVerbose();
#ifdef __LUNA_DEBUG
    end = clock();
    fprintf(stderr, "Runtime  %.2f sec\n", (double) (end - start) / CLOCKS_PER_SEC);    
#endif

    MI = mallinfo();
    fprintf(stdout, "Allocated memory : %d kilobytes\n" , 
	    (MI.uordblks + MI.usmblks) / 1024);
  }
  
  return(0);
}
// Reads the data and serializes it into the message. This function does custom serialization for the same
// reason and with the same alrogithm as DeserializeAndWriteMessage.
HRESULT CFileRepServer::ReadAndSendChunk(
    __in CRequest* request,
    __in long chunkSize, 
    __in LONGLONG chunkPosition,
    __in HANDLE file)
{
    PrintVerbose(L"Entering CFileRepServer::ReadAndSendChunk");

    if (chunkSize < 0 || chunkPosition < 0)
    {
        PrintVerbose(L"Leaving CFileRepServer::ReadAndSendChunk");
        return E_INVALIDARG;
    }

    HRESULT hr = S_OK;
    WS_XML_WRITER* writer = NULL;
    WS_MESSAGE* replyMessage = request->GetReplyMessage();
    WS_MESSAGE* requestMessage = request->GetRequestMessage();
    WS_ERROR* error = request->GetError();
    WS_CHANNEL* channel = request->GetChannel();

    BYTE* buf = NULL;
    LONG length = 0;

    // To avoid using too much memory we read and write the message in chunks.
    LONG bytesToRead = FILE_CHUNK;
    if (bytesToRead > chunkSize)
    {
        bytesToRead = chunkSize;
    }

    buf = (BYTE*)HeapAlloc(GetProcessHeap(), 0, bytesToRead);
    IfNullExit(buf);

    IfFailedExit(WsInitializeMessage(replyMessage, WS_BLANK_MESSAGE, requestMessage, error));

    // Add the action header
    IfFailedExit(WsSetHeader(
        replyMessage,
        WS_ACTION_HEADER,
        WS_XML_STRING_TYPE,
        WS_WRITE_REQUIRED_VALUE,
        &fileReplyAction,
        sizeof(fileReplyAction),
        error));

    // Send the message headers
    IfFailedExit(WsWriteMessageStart(channel, replyMessage, NULL, error));

    // Get writer to serialize message body
    IfFailedExit(WsGetMessageProperty(replyMessage, WS_MESSAGE_PROPERTY_BODY_WRITER, &writer, sizeof(writer), error));

    // Write FileChunk start element.
    // This whole code block is the serialization equivalent of the desiralization code.
    IfFailedExit(WsWriteStartElement(writer, NULL, &fileChunkLocalName, &fileChunkNamespace, error));

    // Write chunkPosition element
    IfFailedExit(WsWriteStartElement(writer, NULL, &chunkPositionLocalName, &fileChunkNamespace, error));
    IfFailedExit(WsWriteValue(writer, WS_INT64_VALUE_TYPE, &chunkPosition, sizeof(chunkPosition), error));
    IfFailedExit(WsWriteEndElement(writer, error));

    // Write fileContent start element
    IfFailedExit(WsWriteStartElement(writer, NULL, &fileContentLocalName, &fileChunkNamespace, error));

    // Like in the deserialization code, we read the file in multiple steps to avoid
    // having to have everything in memory at once. The message could potentially be
    // big so this is more efficient.
    for (;;)
    {
        ULONG bytesRead = 0;

        if (length + bytesToRead > chunkSize)
        {
            bytesToRead = chunkSize - length;
        }

        if (!ReadFile(file, buf, bytesToRead, &bytesRead, NULL))
        {

            PrintError(L"File read error.", true);
            hr = HRESULT_FROM_WIN32(GetLastError());

            EXIT_FUNCTION
        }

        if (0 == bytesRead)
        {
            // We reched the end of the file before filling the chunk. Send a partial chunk.
            break;
        }

        IfFailedExit(WsWriteBytes(writer, buf, bytesRead, error));

        length += bytesRead;

        if (length == chunkSize)
        {
            // We filled the message
            break;
        }
    }
// Performs the actual file transfer.
// This function will fail to produce a valid file on the client if the file was changed in between requests for chunks.
// There are ways to work around that, but doing so is beyond the scope of this version of the sample. A simple fix would be
// to keep the file open between requests and prevent writing, but in the spirit of web services this app does not maintain
// state between requests.
HRESULT CFileRepServer::ReadAndSendFile(
    __in CRequest* request, 
    __in const LPWSTR fileName, 
    __in LONGLONG chunkPosition, 
    __in_opt WS_ERROR* error)
{
    PrintVerbose(L"Entering CFileRepServer::ReadAndSendFile");

    HANDLE file = NULL;
    HRESULT hr = S_OK;

    file = CreateFileW(fileName, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);

    if (INVALID_HANDLE_VALUE == file)
    {
        PrintInfo(L"Invalid file name");
        if (-1 != chunkPosition)
        {
            hr = SendError(request, GlobalStrings::invalidFileName);
        }
        else
        {
            hr = SendFileInfo(request, fileName, -1, chunkSize);
        }

        PrintVerbose(L"Leaving CFileRepServer::ReadAndSendFile");
        return hr;
    }

    LARGE_INTEGER len;

    if (!GetFileSizeEx(file, &len))
    {
        hr = HRESULT_FROM_WIN32(GetLastError());
        PrintError(L"Unable to determine file length", true);
        if (FAILED(SendError(request, GlobalStrings::unableToDetermineFileLength)))
        {
            PrintError(L"Unable to send failure back", true);
        }

        if (!CloseHandle(file))
        {
            PrintError(L"Unable to close file handle", true);
        }

        // This has its own return path to ensure that the right error info is returned.
        // The main error path would overwrite it.
        PrintVerbose(L"Leaving CFileRepServer::ReadAndSendFile");
        return hr;
    }

    LONGLONG fileLength = len.QuadPart;

    if (chunkPosition == DISCOVERY_REQUEST)
    {
        PrintInfo(L"Processing discovery message");
        hr = SendFileInfo(request, fileName, fileLength, chunkSize);
    }
    else if (chunkPosition < -1)
    {
        PrintInfo(L"Invalid request");
        hr = SendError(request, GlobalStrings::invalidRequest);
    }
    else if (chunkPosition >= fileLength)
    {
        PrintInfo(L"Request out of range of the file");
        hr = SendError(request, GlobalStrings::outOfRange);
    }
    else
    {
        long chunkSize = this->chunkSize;
        if (fileLength - chunkPosition < chunkSize)
        {
            chunkSize = (DWORD)(fileLength - chunkPosition);
        }

        LARGE_INTEGER pos;
        pos.QuadPart = chunkPosition;

        if (!SetFilePointerEx(file, pos, NULL, FILE_BEGIN))
        {
            PrintError(L"Unable to set file pointer", true);
            hr = E_FAIL;

            // Ignore return value as we already have a failure.
            SendError(request, GlobalStrings::unableToSetFilePointer);

        }
        else
        {
            hr = ReadAndSendChunk(request, chunkSize, chunkPosition, file);
        }
    }

    if (FAILED(hr))
    {
        PrintError(L"CFileRepServer::ReadAndSendFile\n", true);
        PrintError(hr, error, true);
    }

    if (!CloseHandle(file))
    {
        hr = HRESULT_FROM_WIN32(GetLastError());
        PrintError(L"Unable to close file handle", true);
    }

    PrintVerbose(L"Leaving CFileRepServer::ReadAndSendFile");
    return hr;
}
Exemplo n.º 20
0
void PruneLinedefs(void)
{
  int i;
  int new_num;

  DisplayTicker();

  // scan all linedefs
  for (i=0, new_num=0; i < num_linedefs; i++)
  {
    linedef_t *L = lev_linedefs[i];

    // handle duplicated vertices
    while (L->start->equiv)
    {
      L->start->ref_count--;
      L->start = L->start->equiv;
      L->start->ref_count++;
    }

    while (L->end->equiv)
    {
      L->end->ref_count--;
      L->end = L->end->equiv;
      L->end->ref_count++;
    }

    // handle duplicated sidedefs
    while (L->right && L->right->equiv)
    {
      L->right->ref_count--;
      L->right = L->right->equiv;
      L->right->ref_count++;
    }

    while (L->left && L->left->equiv)
    {
      L->left->ref_count--;
      L->left = L->left->equiv;
      L->left->ref_count++;
    }

    // remove zero length lines
    if (L->zero_len)
    {
      L->start->ref_count--;
      L->end->ref_count--;

      UtilFree(L);
      continue;
    }

    L->index = new_num;
    lev_linedefs[new_num++] = L;
  }

  if (new_num < num_linedefs)
  {
    PrintVerbose("Pruned %d zero-length linedefs\n", num_linedefs - new_num);
    num_linedefs = new_num;
  }

  if (new_num == 0)
    FatalError("Couldn't find any Linedefs");
}
Exemplo n.º 21
0
/* 
 *  ======== main ========
 */ 
INT main(INT argc, CHAR * argv[]) 
{
	INT opt;
	bool fWaitForTerminate = false;
	UINT uProcId = 0;	/* default proc ID is 0. */
	bool fError = false;
	DSP_HPROCESSOR hProc;
	int status = 0;
	INT cArgc = 0;		/* local argc count. */
	bool fScriptable = false;
	extern char *optarg;
	struct DSP_PROCESSORINFO dspInfo;
	UINT numProcs;
	UINT index = 0;
	while ((opt = getopt(argc, argv, "+T+v+w+?p:")) != EOF) {
		switch (opt) {
		case 'v':
			/* verbose mode */ 
			fprintf(stdout, "Verbose mode: ON\n");
			g_fVerbose = true;
			cArgc++;
			break;
		case 'w':
			/* wait for user input to terminate */ 
			fprintf(stdout, "Not supported \n");
			fWaitForTerminate = true;
			cArgc++;
			break;
		case 'T':
			fScriptable = true;
			cArgc++;
			break;
		case 'p':
			/* user specified DSP processor ID (based on zero-index) */ 
			uProcId = atoi(optarg);
			cArgc++;
			break;
		case '?':
		default:
			fError = true;
			break;
		}
	}
	argv += cArgc + 1;
	argc -= cArgc + 1;
	if (fError) {
		DisplayUsage();
	} else {
		status = (DBAPI)DspManager_Open(ROOT_ACCESS, NULL);
		if (DSP_FAILED(status)) {
			PrintVerbose("DSPManager_Open failed \n");
			return -1;
		} 
		while (DSP_SUCCEEDED(DSPManager_EnumProcessorInfo(index,&dspInfo,
						(UINT)sizeof(struct DSP_PROCESSORINFO),&numProcs))) {
			if ((dspInfo.uProcessorType == DSPTYPE_55) || 
									(dspInfo.uProcessorType == DSPTYPE_64)) {
				printf("DSP device detected !! \n");
				uProcId = index;
				status = 0;
				break;
			}
			index++;
		}
		status = DSPProcessor_Attach(uProcId, NULL, &hProc);
		if (DSP_SUCCEEDED(status)) {
			PrintVerbose("DSPProcessor_Attach succeeded.\n");
			status = DSPProcessor_Stop(hProc);
			if (DSP_SUCCEEDED(status)) {
				PrintVerbose("DSPProcessor_Stop succeeded.\n");
				status = DSPProcessor_Load(hProc,argc,(CONST CHAR **)argv,NULL);
				if (DSP_SUCCEEDED(status)) {
					PrintVerbose("DSPProcessor_Load succeeded.\n");
					status = DSPProcessor_Start(hProc);
					if (DSP_SUCCEEDED(status)) {
						fprintf(stdout,"DSPProcessor_Start succeeded.\n");
#if 0                    
						/* It seems Linux bridge does n't yet support
						 * * DSPProcessor_GetTrace */ 
						if (fWaitForTerminate) { 
							/* wait for user */ 
							fprintf(stdout,"Hit \"return\" to stop DSP and"
													"dump trace buffer:\n");
							(void)getchar();
							status = DSPProcessor_GetTrace(hProc,
												(BYTE *)&traceBuf,MAXTRACESIZE);
							fprintf(stdout,"%s\n",traceBuf);
						} else {
							PrintVerbose("in run free mode...\n");
						}
#endif	/* 0 */
					} else {
						PrintVerbose("DSPProcessor_Start failed: 0x%x.\n",
																		status);
					}
				} else {
					PrintVerbose("DSPProcessor_Load failed: 0x%x.\n",status);
				}
				DSPProcessor_Detach(hProc);
			}
		} else {
			PrintVerbose("DSPProcessor_Attach failed: 0x%x.\n",status);
		}
	}
	if (!fScriptable) {
		/* Wait for user to hit any key before exiting. */ 
		fprintf(stdout, "Hit any key to terminate cexec.\n");
		(void)getchar();
	}
	status = DspManager_Close(0, NULL);
	if (DSP_FAILED(status)) {
		printf("\nERROR: DSPManager Close FAILED\n");
	}
	return (DSP_SUCCEEDED(status) ? 0 : -1);
}
Exemplo n.º 22
0
int main(int argc, char **argv)
{
	int i, j, k, treeNo, sumLength;
	char ch;
	TTree **treeSet;
	FILE *text_fv;
	clock_t totalStart;
	double totalSecs, scale, sum;
	char *ancestor;

	totalStart = clock();

	ReadParams(argc, argv);

	if (rateHetero == CodonRates && invariableSites) {
		fprintf(stderr, "Invariable sites model cannot be used with codon rate heterogeneity.\n");
		exit(4);
	}

	if (writeAncestors && fileFormat == NEXUSFormat) {
		fprintf(stderr, "Warning - When writing ancestral sequences, relaxed PHYLIP format is used.\n");
	}

	if (writeAncestors && maxPartitions > 1) {
		fprintf(stderr, "Writing ancestral sequences can only be used for a single partition.\n");
		exit(4);
	}
			
	if (!userSeed)
		randomSeed = CreateSeed();
		
	SetSeed(randomSeed);

	if (!quiet)
 		PrintTitle();
	
	numTrees = OpenTreeFile();

	/* if (!treeFile) { */
		ReadFileParams();
	/*} */


	if ((ancestorSeq>0 && !hasAlignment) || ancestorSeq>numSequences) {
		fprintf(stderr, "Bad ancestral sequence number: %d (%d sequences loaded)\n", ancestorSeq, numSequences);
		exit(4);
	}
	
	if (textFile) {
		if ( (text_fv=fopen(textFileName, "rt"))==NULL ) {
			fprintf(stderr, "Error opening text file for insertion into output: '%s'\n", textFileName);
			exit(4);
		}
	}

	ancestor=NULL;
	if (hasAlignment) {
		AllocateMemory();	
		ReadFile();
		
		if (numSites<0)
			numSites=numAlignmentSites;		
			
		if (ancestorSeq>0) {
			if (numSites!=numAlignmentSites) {
				fprintf(stderr, "Ancestral sequence is of a different length to the simulated sequences (%d)\n", numAlignmentSites);
				exit(4);
			}
			ancestor=sequences[ancestorSeq-1];
		}
	} else if (numSites<0)
		numSites=1000;
	
	SetModel(model);
	
	numTaxa=-1;
	scale=1.0;
	
	treeSet = (TTree **)malloc(sizeof(TTree **) * maxPartitions);
	if (treeSet==NULL) {
		fprintf(stderr, "Out of memory\n");
		exit(5);
	}
	
	partitionLengths = (int *)malloc(sizeof(int) * maxPartitions);
	if (partitionLengths==NULL) {
		fprintf(stderr, "Out of memory\n");
		exit(5);
	}
	
	partitionRates = (double *)malloc(sizeof(double) * maxPartitions);
	if (partitionRates==NULL) {
		fprintf(stderr, "Out of memory\n");
		exit(5);
	}
	
	for (i = 0; i < maxPartitions; i++) {
		if ((treeSet[i]=NewTree())==NULL) {
			fprintf(stderr, "Out of memory\n");
			exit(5);
		}
	}
					
	CreateRates();
	
	treeNo=0;
	do {
		partitionLengths[0] = -1;
		ReadTree(tree_fv, treeSet[0], treeNo+1, 0, NULL, &partitionLengths[0], &partitionRates[0]);

		if (treeNo==0) {
			numTaxa=treeSet[0]->numTips;
			
			if (!quiet)
				fprintf(stderr, "Random number generator seed: %ld\n\n", randomSeed);
				
			if (fileFormat == NEXUSFormat) {
				fprintf(stdout, "#NEXUS\n");
				fprintf(stdout, "[\nGenerated by %s %s\n\n", PROGRAM_NAME, VERSION_NUMBER);
				PrintVerbose(stdout);
				fprintf(stdout, "]\n\n");
			}
		} else if (treeSet[0]->numTips != numTaxa) {
			fprintf(stderr, "All trees must have the same number of tips.\n");
			exit(4);
		}
		
		if (maxPartitions == 1) {
			if (partitionLengths[0] != -1) {
				fprintf(stderr, "\nWARNING: The treefile contained partion lengths but only one partition\n");
				fprintf(stderr, "was specified.\n");
			}
			partitionLengths[0] = numSites;
		}

		sumLength = partitionLengths[0];
		i = 1;
		while (sumLength < numSites && i <= maxPartitions) {
			if (!IsTreeAvail(tree_fv)) {
				fprintf(stderr, "\nA set of trees number %d had less partition length (%d) than\n", treeNo + 1, sumLength);
				fprintf(stderr, "was required to make a sequence of length %d.\n", numSites);
				exit(4);
			}
				
			ReadTree(tree_fv, treeSet[i], treeNo+1, treeSet[0]->numTips, treeSet[0]->names, 
						&partitionLengths[i], &partitionRates[i]);
						
			if (treeSet[i]->numTips != numTaxa) {
				fprintf(stderr, "All trees must have the same number of tips.\n");
				exit(4);
			}
			
			sumLength += partitionLengths[i];
			i++;
		}
		if (i > maxPartitions) {
			fprintf(stderr, "\nA set of trees number %d had more partitions (%d) than\n", treeNo + 1, i);
			fprintf(stderr, "was specified in the user options (%d).\n", maxPartitions);
		}
		numPartitions = i;
				
		if (sumLength != numSites) {
			fprintf(stderr, "The sum of the partition lengths in the treefile does not equal\n");
			fprintf(stderr, "the specified number of sites.\n");
			exit(4);
		}
			
		for (i = 0; i < numPartitions; i++)
			CreateSequences(treeSet[i], partitionLengths[i]);
		
		if (numPartitions > 1) {
			sum = 0.0;
			for (i = 0; i < numPartitions; i++)
				sum += partitionRates[i] * partitionLengths[i];
				
			for (i = 0; i < numPartitions; i++)
				partitionRates[i] *= numSites / sum;
		}
		
		if (treeNo==0 && verbose && !quiet) {
			PrintVerbose(stderr);
			InitProgressBar(numTrees*numDatasets);
			DrawProgressBar();
		}

		for (i=0; i<numDatasets; i++) {
			SetCategories();
			
			k = 0;
			for (j = 0; j < numPartitions; j++) {
				scale = partitionRates[j];
				
				if (scaleTrees) { 
					if (!treeSet[j]->rooted) {
						fprintf(stderr, "To scale tree length, they must be rooted and ultrametric.\n");
						exit(4);
					}
					scale *= treeScale/treeSet[j]->totalLength;
				} else if (scaleBranches)
					scale *= branchScale;

				EvolveSequences(treeSet[j], k, partitionLengths[j], scale, ancestor);
				k += partitionLengths[j];
			}
			
			if (writeAncestors)
				WriteAncestralSequences(stdout, treeSet[0]);
			else
				WriteSequences(stdout, (numTrees > 1 ? treeNo+1 : -1), (numDatasets > 1 ? i+1 : -1), treeSet, partitionLengths);

			if (writeRates) {
				WriteRates(stderr);
			}

			if (textFile) {
				while (!feof(text_fv)) {
					ch = fgetc(text_fv);
					if (!feof(text_fv))
						fputc(ch, stdout);
				}
				fputc('\n', stdout);
				rewind(text_fv);
			}
			
			if (verbose && !quiet)
				ProgressBar();
		}
				
		for (i = 0; i < numPartitions; i++)
			DisposeTree(treeSet[i]);
			
		treeNo++;
	} while (IsTreeAvail(tree_fv));
	
/*	for (i = 0; i < maxPartitions; i++)
		FreeTree(treeSet[i]);	*/
	
	if (treeFile)
		fclose(tree_fv);

	if (textFile)
		fclose(text_fv);

	totalSecs = (double)(clock() - totalStart) / CLOCKS_PER_SEC;
	if (!quiet) {
		fprintf(stderr, "Time taken: %G seconds\n", totalSecs);
		if (verboseMemory)
			fprintf(stderr, "Total memory used: %ld\n", totalMem);
	}
	
	return 0;
}