Существуют формальные языки для определения семантики; вы можете видеть такие языки и определения практически в любом техническом документе в материалах конференций по языкам программирования. Тексты по этой теме доступны: https://mitpress.mit.edu/.../semantics-programming-languages Вам нужно иметь готовность прочитать сжатые математические обозначения.
Практически, эти семантики не используются для управления переводами/компиляторами; это все еще тема исследования. См. http://Fwww.andrew.cmu.edu%2Fuser%2Fasubrama%2Fdissertation.pdf. Чтобы прочитать их, вам, как правило, нужно некоторое время прочесть вводные тексты, такие как выше.
Было проведено более практическую работу по определению переводов; наиболее практичными являются program transformation systems. С такими инструментами, можно написать, используя обозначения языка-источника (например, ваш DSL), а также обозначение целевого языка (например, Java или ассемблер или любой другой), правила преобразования формы:
replace source_language_fragment by target_language_fragment if condition
Эти инструменты управляются грамматикой для исходного и целевого языков и интерпретируют правила преобразования из их читаемой формы в AST-AST для перезаписывания. Для полного перевода сложного DSL на другой язык обычно требуются сотни правил, но ключевым моментом является то, что их гораздо легче читать, чем процедурный код, типичный для письменных переводчиков.
Пытаясь следовать примеру OP, в предположении, один имеют грамматики для «MyDSL» Ора и для «Java» в качестве цели, и используя стиль нашего DMS программного обеспечения Reengineeering Инструментов правил преобразования:
source domain dsl;
target domain Java;
rule translate_single_assignment(t: dsl_IDENTIFIER, e: dsl_expression):
" \t = \e " -- MyDSL syntax
-> -- read as "rewrites to"
" int \JavaIdentifier\(\t\)=\e;
".
rule translate_multi_assignment(t1: dsl_IDENTIFIER, t2: dsl_IDENTIFIER, e: dsl_expression):
" \t1 = \t2 = \e " -- MyDSL syntax
-> -- read as "rewrites to"
" \>\dsl \t2 = \e \statement
int \t1;
\t1=\t2;
".
Вам нужно два правила: один для базового случая простого назначения t = e; и один для обработки множественного случая назначения. Случай множественного присваивания отменяет самое внешнее назначение, и генерирует для него код и вставляет оставшуюся часть множественного присваивания обратно в исходную форму DSL для обработки одним из двух правил.
Вы можете увидеть еще один пример этого используется для рефакторинга (SOURCE_LANGUAGE == TARGET_LANGUAGE) в https://stackoverflow.com/questions/22094428/programmatic-refactoring-of-java-source-files/22100670#22100670
Я не знаю, есть ли формальный язык для определения семантики, но если вы хотите примеры того, как это обычно сделайте, посмотрите, например глава 6 стандарта [C] (http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1570.pdf) или [Java JLS] (http://docs.oracle .com/JavaSE/функции/JLS/SE7/HTML/index.html). –