浏览代码

Add em_asm intrinsic

hermansimensen 2 年之前
父节点
当前提交
6bde23b75e
共有 1 个文件被更改,包括 44 次插入2 次删除
  1. 44 2
      IDEHelper/Compiler/BfIRCodeGen.cpp

+ 44 - 2
IDEHelper/Compiler/BfIRCodeGen.cpp

@@ -3075,11 +3075,53 @@ void BfIRCodeGen::HandleNextCmd()
 				switch (intrinsicData->mIntrinsic)
 				{
 				case BfIRIntrinsic__PLATFORM:
+				{
+					if (intrinsicData->mName == "em_asm_internal")
 					{
-						FatalError(StrFormat("Unable to find intrinsic '%s'", intrinsicData->mName.c_str()));
+						llvm::StringRef strContent;
+						llvm::ConstantDataArray* dataArray;
+						if (const llvm::ConstantExpr* ce = llvm::dyn_cast<llvm::ConstantExpr>(args[0]))
+						{
+							llvm::Value* firstOperand = ce->getOperand(0);
+							if (llvm::GlobalVariable* gv = llvm::dyn_cast<llvm::GlobalVariable>(firstOperand))
+							{
+								if (gv->getType()->isPointerTy())
+								{
+									if (dataArray = llvm::dyn_cast<llvm::ConstantDataArray>(gv->getInitializer()))
+									{
+										strContent = dataArray->getAsString();
+									}
+								}
+							}
+						}
+						else
+							FatalError("Value is not ConstantExpr");
+						
+
+						auto charType = llvm::IntegerType::get(*mLLVMContext, 8);
+						std::vector<llvm::Constant*> chars(strContent.size());
+						for (unsigned int i = 0; i < strContent.size(); i++)
+						{
+							chars[i] = llvm::ConstantInt::get(charType, strContent[i]);;
+						}
+						
+						chars.push_back(llvm::ConstantInt::get(charType, 0));
+						auto stringType = llvm::ArrayType::get(charType, chars.size());
+						
+						auto globalVar = (llvm::GlobalVariable*)mLLVMModule->getOrInsertGlobal("", stringType);
+						globalVar->setSection("em_asm");
+						globalVar->setInitializer(llvm::ConstantArray::get(stringType, chars));
+						globalVar->setConstant(true);
+						globalVar->setLinkage(llvm::GlobalValue::LinkageTypes::ExternalLinkage);
+						globalVar->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
+						
+						SetResult(curId, llvm::ConstantExpr::getBitCast(globalVar, charType->getPointerTo()));
+						break;
 					}
-					break;
 
+					FatalError(StrFormat("Unable to find intrinsic '%s'", intrinsicData->mName.c_str()));
+					break;
+				}
 				case BfIRIntrinsic_Add:
 				case BfIRIntrinsic_And:
 				case BfIRIntrinsic_Div: