Skip to content

Commit

Permalink
Trench deposition example
Browse files Browse the repository at this point in the history
  • Loading branch information
tobre1 committed Nov 14, 2024
1 parent 71c8ebb commit 22350ba
Show file tree
Hide file tree
Showing 9 changed files with 308 additions and 303 deletions.
13 changes: 6 additions & 7 deletions gpu/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ set(VIENNAPS_GPU_INCLUDE_DIRS #
${CMAKE_SOURCE_DIR}/app
${PROJECT_SOURCE_DIR} ${PROJECT_SOURCE_DIR}/geometry ${PROJECT_SOURCE_DIR}/process
${PROJECT_SOURCE_DIR}/rayTracing ${PROJECT_SOURCE_DIR}/utils ${PROJECT_SOURCE_DIR}/app
${PROJECT_SOURCE_DIR}/models
${ViennaCore_SOURCE_DIR}/include/viennacore
)

Expand Down Expand Up @@ -89,13 +90,11 @@ add_dependencies(buildGPUApplication ViennaPS_GPU)

add_custom_target(buildGPUExamples)

# add_executable(GPU_Trench ${embedded_SF6O2_pipeline}
# ${PROJECT_SOURCE_DIR}/examples/trench.cpp)
# target_include_directories(
# GPU_Trench PUBLIC ${VIENNAPS_INCLUDE_DIRS} ${OptiX_INCLUDE}
# ${VIENNAPS_GPU_INCLUDE_DIRS} ${CMAKE_SOURCE_DIR}/app)
# target_link_libraries(GPU_Trench ${CUDA_LIBRARIES} ${CUDA_CUDA_LIBRARY} ViennaPS)
# add_dependencies(buildGPUExamples GPU_Trench)
add_executable(GPU_Trench ${embedded_SingleParticle_pipeline}
${PROJECT_SOURCE_DIR}/examples/trench.cpp)
target_include_directories(GPU_Trench PUBLIC ${OptiX_INCLUDE} ${VIENNAPS_GPU_INCLUDE_DIRS})
target_link_libraries(GPU_Trench ${CUDA_LIBRARIES} ${CUDA_CUDA_LIBRARY} ViennaPS)
add_dependencies(buildGPUExamples GPU_Trench)

# add_executable(GPU_Hole ${embedded_SF6O2_pipeline}
# ${PROJECT_SOURCE_DIR}/examples/hole.cpp)
Expand Down
153 changes: 27 additions & 126 deletions gpu/examples/trench.cpp
Original file line number Diff line number Diff line change
@@ -1,145 +1,46 @@
#include <SF6O2Etching.hpp>
#include <psMakePlane.hpp>
#include <psUtils.hpp>
#include <psWriteVisualizationMesh.hpp>
#include <geometries/psMakeTrench.hpp>

#include <psProcess.hpp>
#include <pscuProcess.hpp>
#include <pscuProcessPipelines.hpp>
#include <pscuSingleParticleProcess.hpp>

using namespace viennaps;

int main(int argc, char **argv) {

omp_set_num_threads(16);
constexpr int D = 3;
using NumericType = float;

pscuContext context;
pscuCreateContext(context);
psLogger::setLogLevel(psLogLevel::INTERMEDIATE);

const float gridDelta = 1.;
const float extent = 100.;
const float trenchWidth = 15.;
const float spacing = 20.;
const float maskHeight = 40.;

const float time = 3.;
const float ionFlux = 1.;
const float etchantFlux = 1000.;
const float oxygenFlux = 500.;
const float ionEnergy = 100.;
const float ionSigma = 10.;
const float exponent = 1000.;

auto domain = psSmartPointer<psDomain<float, D>>::New();

{
double extent2 = extent / 2.;
double bounds[2 * D] = {-extent2, extent2, -extent2,
extent2, -extent2, extent2};
typename lsDomain<float, D>::BoundaryType boundaryCons[D] = {
lsDomain<float, D>::BoundaryType::REFLECTIVE_BOUNDARY,
lsDomain<float, D>::BoundaryType::REFLECTIVE_BOUNDARY,
lsDomain<float, D>::BoundaryType::INFINITE_BOUNDARY};

float origin[D] = {0., 0., maskHeight};
float normal[D] = {0., 0., 1.};

auto mask = psSmartPointer<lsDomain<float, D>>::New(bounds, boundaryCons,
gridDelta);
lsMakeGeometry<float, D>(
mask, lsSmartPointer<lsPlane<float, D>>::New(origin, normal))
.apply();
normal[2] = -1.;
origin[2] = 0.;
auto maskUnder = psSmartPointer<lsDomain<float, D>>::New(
bounds, boundaryCons, gridDelta);
lsMakeGeometry<float, D>(
maskUnder, lsSmartPointer<lsPlane<float, D>>::New(origin, normal))
.apply();
lsBooleanOperation<float, D>(mask, maskUnder).apply();

auto trench = psSmartPointer<lsDomain<float, D>>::New(bounds, boundaryCons,
gridDelta);
float minPoint[D] = {-extent2 + spacing, extent2 - spacing - trenchWidth,
-gridDelta};
float maxPoint[D] = {extent2 - spacing, extent2 - spacing,
maskHeight + gridDelta};
gpu::Context context;
gpu::CreateContext(context);
Logger::setLogLevel(LogLevel::DEBUG);

lsMakeGeometry<float, D>(
trench, lsSmartPointer<lsBox<float, D>>::New(minPoint, maxPoint))
.apply();
lsBooleanOperation<float, D>(mask, trench,
lsBooleanOperationEnum::RELATIVE_COMPLEMENT)
.apply();
const NumericType gridDelta = 1.0;
const NumericType extent = 100.;
const NumericType trenchWidth = 15.;
const NumericType maskHeight = 40.;

minPoint[0] = -extent2 + spacing;
minPoint[1] = -extent2 - gridDelta;
maxPoint[0] = -extent2 + spacing + trenchWidth;
maxPoint[1] = extent2 - spacing - trenchWidth + gridDelta;
const NumericType time = 10.;
const NumericType sticking = .1;
const NumericType rate = 1.0;
const NumericType exponent = 1.;

lsMakeGeometry<float, D>(
trench, lsSmartPointer<lsBox<float, D>>::New(minPoint, maxPoint))
.apply();
lsBooleanOperation<float, D>(mask, trench,
lsBooleanOperationEnum::RELATIVE_COMPLEMENT)
.apply();
auto domain = SmartPointer<Domain<NumericType, D>>::New();

domain->insertNextLevelSetAsMaterial(mask, psMaterial::Mask);
}
MakeTrench<NumericType, D>(domain, gridDelta, extent, extent, trenchWidth,
maskHeight, 0., 0., false, false, Material::Si)
.apply();
domain->saveSurfaceMesh("trench_initial.vtp");

psMakePlane<float, D>(domain, 0., psMaterial::Si).apply();
domain->printSurface("trench_initial.vtp");
auto model = SmartPointer<gpu::SingleParticleProcess<NumericType, D>>::New(
rate, sticking, exponent);

curtParticle<float> ion{.name = "ion",
.numberOfData = 3,
.cosineExponent = exponent,
.meanIonEnergy = ionEnergy,
.sigmaIonEnergy = ionSigma,
.A_O = 3.f};
ion.dataLabels.push_back("ionSputteringRate");
ion.dataLabels.push_back("ionEnhancedRate");
ion.dataLabels.push_back("oxygenSputteringRate");
gpu::Process<NumericType, D> process(context, domain, model, time);
process.setNumberOfRaysPerPoint(3000);

curtParticle<float> etchant{.name = "etchant", .numberOfData = 2};
etchant.dataLabels.push_back("etchantRate");
etchant.dataLabels.push_back("sticking_e");

curtParticle<float> oxygen{.name = "oxygen", .numberOfData = 2};
oxygen.dataLabels.push_back("oxygenRate");
oxygen.dataLabels.push_back("sticking_o");

auto surfModel =
psSmartPointer<SF6O2Implementation::SurfaceModel<float, DIM>>::New(
ionFlux, etchantFlux, oxygenFlux, -100000);
auto velField = psSmartPointer<psDefaultVelocityField<float>>::New(2);
auto model = psSmartPointer<pscuProcessModel<float>>::New();

model->insertNextParticleType(ion);
model->insertNextParticleType(etchant);
model->insertNextParticleType(oxygen);
model->setSurfaceModel(surfModel);
model->setVelocityField(velField);
model->setProcessName("SF6O2Etching");
model->setPtxCode(embedded_SF6O2_pipeline);

// auto model = psSmartPointer<SF6O2Etching<float, D>>::New(
// ionFlux, etchantFlux, oxygenFlux, ionEnergy, ionSigma, exponent, 3.);

pscuProcess<float, D> process(context);
process.setDomain(domain);
process.setProcessModel(model);
process.setNumberOfRaysPerPoint(1000);
process.setMaxCoverageInitIterations(30);
process.setProcessDuration(time);
process.setSmoothFlux(2.);

psUtils::Timer timer;
timer.start();
domain->duplicateTopLevelSet(Material::SiO2);
process.apply();
timer.finish();

std::cout << "Process took: " << timer.currentDuration * 1e-9 << " s"
<< std::endl;

domain->printSurface("trench_etched.vtp");
domain->saveSurfaceMesh("trench_etched.vtp");
}
70 changes: 70 additions & 0 deletions gpu/models/pscuSingleParticleProcess.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
#pragma once

#include <models/psSingleParticleProcess.hpp>

#include <pscuProcessModel.hpp>
#include <pscuProcessPipelines.hpp>

namespace viennaps {

namespace gpu {

template <typename NumericType, int D>
class SingleParticleProcess : public ProcessModel<NumericType> {
public:
SingleParticleProcess(NumericType rate = 1.,
NumericType stickingProbability = 1.,
NumericType sourceDistributionPower = 1.,
Material maskMaterial = Material::None) {
std::unordered_map<Material, NumericType> maskMaterialMap = {
{maskMaterial, 0.}};
initialize(rate, stickingProbability, sourceDistributionPower,
std::move(maskMaterialMap));
}

SingleParticleProcess(NumericType rate, NumericType stickingProbability,
NumericType sourceDistributionPower,
std::vector<Material> maskMaterial) {
std::unordered_map<Material, NumericType> maskMaterialMap;
for (auto &mat : maskMaterial) {
maskMaterialMap[mat] = 0.;
}
initialize(rate, stickingProbability, sourceDistributionPower,
std::move(maskMaterialMap));
}

SingleParticleProcess(std::unordered_map<Material, NumericType> materialRates,
NumericType stickingProbability,
NumericType sourceDistributionPower) {
initialize(0., stickingProbability, sourceDistributionPower,
std::move(materialRates));
}

private:
void initialize(NumericType rate, NumericType stickingProbability,
NumericType sourceDistributionPower,
std::unordered_map<Material, NumericType> &&maskMaterial) {
// particles

Particle<NumericType> particle{.name = "SingleParticle",
.sticking = stickingProbability,
.cosineExponent = sourceDistributionPower};
particle.dataLabels.push_back("particleFlux");

// surface model
auto surfModel = SmartPointer<::viennaps::impl::SingleParticleSurfaceModel<
NumericType, D>>::New(rate, maskMaterial);

// velocity field
auto velField =
SmartPointer<::viennaps::DefaultVelocityField<NumericType>>::New(2);

this->setPtxCode(embedded_SingleParticle_pipeline);
this->setSurfaceModel(surfModel);
this->setVelocityField(velField);
this->insertNextParticleType(particle);
this->setProcessName("SingleParticleProcess");
}
};
} // namespace gpu
} // namespace viennaps
Loading

0 comments on commit 22350ba

Please sign in to comment.