public JSGFRuleGrammar NewGrammar(String name) { Debug.Assert(_manager != null); var grammar = new JSGFRuleGrammar(name, _manager); _manager.StoreGrammar(grammar); return(grammar); }
/** * Load named grammar from import rule * * @param grammarName * @return already loaded grammar * @throws JSGFGrammarParseException * @throws IOException */ private JSGFRuleGrammar LoadNamedGrammar(String grammarName) { var url = GrammarNameToUrl(BaseUrl, grammarName); JSGFRuleGrammar ruleGrammar = JSGFParser.NewGrammarFromJSGF(url, new JSGFRuleGrammarFactory(Manager)); ruleGrammar.SetEnabled(true); return(ruleGrammar); }
/** * Parses the given RuleName into a network of GrammarNodes. * * @param initialRuleName * the RuleName rule to parse * @return a grammar graph */ private GrammarGraph ProcessRuleName(JSGFRuleName initialRuleName) { this.LogInfo("parseRuleName: " + initialRuleName); GrammarGraph result = RuleStack.Contains(initialRuleName.GetRuleName()); if (result != null) { // its a recursive call return(result); } else { result = new GrammarGraph(this); RuleStack.Push(initialRuleName.GetRuleName(), result); } JSGFRuleName ruleName = _ruleGrammar.Resolve(initialRuleName); if (ruleName == JSGFRuleName.Null) { result.StartNode.Add(result.EndNode, 0.0f); } else if (ruleName == JSGFRuleName.Void) { // no connection for void } else { if (ruleName == null) { throw new JSGFGrammarException("Can't resolve " + initialRuleName + " g " + initialRuleName.GetFullGrammarName()); } JSGFRuleGrammar rg = Manager.RetrieveGrammar(ruleName .GetFullGrammarName()); if (rg == null) { throw new JSGFGrammarException("Can't resolve grammar name " + ruleName.GetFullGrammarName()); } JSGFRule rule = rg.GetRule(ruleName.GetSimpleRuleName()); if (rule == null) { throw new JSGFGrammarException("Can't resolve rule: " + ruleName.GetRuleName()); } GrammarGraph ruleResult = ProcessRule(rule); if (result != ruleResult) { result.StartNode.Add(ruleResult.StartNode, 0.0f); ruleResult.EndNode.Add(result.EndNode, 0.0f); } } RuleStack.Pop(); return(result); }
/** * Commit changes to all loaded grammars and all changes of grammar since * the last commitChange * * @throws JSGFGrammarParseException * @throws JSGFGrammarException */ public virtual void CommitChanges() { try { if (LoadGrammar) { if (Manager == null) { GetGrammarManager(); } _ruleGrammar = LoadNamedGrammar(GrammarName); LoadImports(_ruleGrammar); LoadGrammar = false; } Manager.LinkGrammars(); RuleStack = new RuleStack(); NewGrammar(); FirstNode = CreateGrammarNode("<sil>"); GrammarNode finalNode = CreateGrammarNode("<sil>"); finalNode.SetFinalNode(true); // go through each rule and create a network of GrammarNodes // for each of them foreach (String ruleName in _ruleGrammar.GetRuleNames()) { if (_ruleGrammar.IsRulePublic(ruleName)) { String fullName = GetFullRuleName(ruleName); GrammarGraph publicRuleGraph = new GrammarGraph(this); RuleStack.Push(fullName, publicRuleGraph); JSGFRule rule = _ruleGrammar.GetRule(ruleName); GrammarGraph graph = ProcessRule(rule); RuleStack.Pop(); FirstNode.Add(publicRuleGraph.StartNode, 0.0f); publicRuleGraph.EndNode.Add(finalNode, 0.0f); publicRuleGraph.StartNode.Add(graph.StartNode, 0.0f); graph.EndNode.Add(publicRuleGraph.EndNode, 0.0f); } } PostProcessGrammar(); if (Logger.Level == LogLevel.All) { DumpGrammar(); } } catch (UriFormatException mue) { throw new IOException("bad base grammar URL " + BaseUrl + ' ' + mue); } }
/** * Load grammars imported by the specified RuleGrammar if they are not * already loaded. * * @throws JSGFGrammarParseException */ private void LoadImports(JSGFRuleGrammar grammar) { foreach (JSGFRuleName ruleName in grammar.Imports) { // System.out.println ("Checking import " + ruleName); String grammarName = ruleName.GetFullGrammarName(); JSGFRuleGrammar importedGrammar = GetNamedRuleGrammar(grammarName); if (importedGrammar == null) { // System.out.println ("Grammar " + grammarName + // " not found. Loading."); importedGrammar = LoadNamedGrammar(ruleName .GetFullGrammarName()); } if (importedGrammar != null) { LoadImports(importedGrammar); } } LoadFullQualifiedRules(grammar); }
/** * Load grammars imported by a fully qualified Rule Token if they are not * already loaded. * * @param grammar * @throws IOException * @throws GrammarException * @throws JSGFGrammarParseException */ private void LoadFullQualifiedRules(JSGFRuleGrammar grammar) { // Go through every rule foreach (String ruleName in grammar.GetRuleNames()) { String rule = grammar.GetRule(ruleName).ToString(); // check for rule-Tokens int index = 0; while (index < rule.Length) { index = rule.IndexOf('<', index); if (index < 0) { break; } // Extract rule name var endIndex = rule.IndexOf('>', index + 1); JSGFRuleName extractedRuleName = new JSGFRuleName(rule .Substring(index + 1, endIndex - (index + 1)) .Trim()); index = endIndex + 1; // Check for full qualified rule name if (extractedRuleName.GetFullGrammarName() != null) { String grammarName = extractedRuleName.GetFullGrammarName(); JSGFRuleGrammar importedGrammar = GetNamedRuleGrammar(grammarName); if (importedGrammar == null) { importedGrammar = LoadNamedGrammar(grammarName); } if (importedGrammar != null) { LoadImports(importedGrammar); } } } } }
/** Resolve and link up all rule references contained in all rules. */ public void ResolveAllRules() { StringBuilder b = new StringBuilder(); // First make sure that all imports are resolvable foreach (JSGFRuleName ruleName in Imports) { String grammarName = ruleName.GetFullGrammarName(); JSGFRuleGrammar GI = _manager.RetrieveGrammar(grammarName); if (GI == null) { b.Append("Undefined grammar ").Append(grammarName).Append(" imported in ").Append(_name).Append('\n'); } } if (b.Length > 0) { throw new JSGFGrammarException(b.ToString()); } foreach (JSGFRuleState state in Rules.Values) { ResolveRule(state.rule); } }
/** * Resolve a simple or qualified rule name as a full rule name. * * @param ruleName * the name of the rule. */ public JSGFRuleName Resolve(JSGFRuleName ruleName) { // System.out.println ("Resolving " + ruleName); JSGFRuleName rn = new JSGFRuleName(ruleName.GetRuleName()); String simpleName = rn.GetSimpleRuleName(); String grammarName = rn.GetSimpleGrammarName(); String packageName = rn.GetPackageName(); String fullGrammarName = rn.GetFullGrammarName(); // Check for badly formed RuleName if (packageName != null && grammarName == null) { throw new JSGFGrammarException("Error: badly formed rulename " + rn); } if (ruleName.GetSimpleRuleName().Equals("NULL")) { return(JSGFRuleName.Null); } if (ruleName.GetSimpleRuleName().Equals("VOID")) { return(JSGFRuleName.Void); } // Check simple case: a local rule reference if (fullGrammarName == null && GetRule(simpleName) != null) { return(new JSGFRuleName(_name + '.' + simpleName)); } // Check for fully-qualified reference if (fullGrammarName != null) { JSGFRuleGrammar g = _manager.RetrieveGrammar(fullGrammarName); if (g != null) { if (g.GetRule(simpleName) != null) { // we have a successful resolution return(new JSGFRuleName(fullGrammarName + '.' + simpleName)); } } } // Collect all matching imports into a list. After trying to // match rn to each import statement the vec will have // size()=0 if rn is unresolvable // size()=1 if rn is properly resolvable // size()>1 if rn is an ambiguous reference List <JSGFRuleName> matches = new List <JSGFRuleName>(); // Get list of imports // Add local grammar to simply the case of checking for // a qualified or fully-qualified local reference. List <JSGFRuleName> imports = new List <JSGFRuleName>(this.Imports); imports.Add(new JSGFRuleName(_name + ".*")); // Check each import statement for a possible match foreach (JSGFRuleName importName in imports) { // TO-DO: update for JSAPI 1.0 String importSimpleName = importName.GetSimpleRuleName(); String importGrammarName = importName.GetSimpleGrammarName(); String importFullGrammarName = importName.GetFullGrammarName(); // Check for badly formed import name if (importFullGrammarName == null) { throw new JSGFGrammarException("Error: badly formed import " + ruleName); } // Get the imported grammar JSGFRuleGrammar gref = _manager.RetrieveGrammar(importFullGrammarName); if (gref == null) { Console.WriteLine("Warning: import of unknown grammar " + ruleName + " in " + _name); continue; } // If import includes simpleName, test that it really exists if (!importSimpleName.Equals("*") && gref.GetRule(importSimpleName) == null) { Console.WriteLine("Warning: import of undefined rule " + ruleName + " in " + _name); continue; } // Check for fully-qualified or qualified reference if (importFullGrammarName.Equals(fullGrammarName) || importGrammarName.Equals(fullGrammarName)) { // Know that either // import <ipkg.igram.???> matches <pkg.gram.???> // OR // import <ipkg.igram.???> matches <gram.???> // (ipkg may be null) if (importSimpleName.Equals("*")) { if (gref.GetRule(simpleName) != null) { // import <pkg.gram.*> matches <pkg.gram.rulename> matches.Add(new JSGFRuleName(importFullGrammarName + '.' + simpleName)); } continue; } else { // Now testing // import <ipkg.igram.iRuleName> against <??.gram.ruleName> // if (importSimpleName.Equals(simpleName)) { // import <pkg.gram.rulename> exact match for // <???.gram.rulename> matches.Add(new JSGFRuleName(importFullGrammarName + '.' + simpleName)); } continue; } } // If we get here and rulename is qualified or fully-qualified // then the match failed - try the next import statement if (fullGrammarName != null) { continue; } // Now test // import <ipkg.igram.*> against <simpleName> if (importSimpleName.Equals("*")) { if (gref.GetRule(simpleName) != null) { // import <pkg.gram.*> matches <simpleName> matches.Add(new JSGFRuleName(importFullGrammarName + '.' + simpleName)); } continue; } // Finally test // import <ipkg.igram.iSimpleName> against <simpleName> if (importSimpleName.Equals(simpleName)) { matches.Add(new JSGFRuleName(importFullGrammarName + '.' + simpleName)); continue; } } // The return behavior depends upon number of matches switch (matches.Count) { case 0: // Return null if rulename is unresolvable return(null); case 1: // Return successfully return(matches[0]); default: // Throw exception if ambiguous reference StringBuilder b = new StringBuilder(); b.Append("Warning: ambiguous reference ").Append(rn).Append(" in ").Append(_name).Append(" to "); foreach (JSGFRuleName tmp in matches) { b.Append(tmp).Append(" and "); } b.Length = (b.Length - 5); throw new JSGFGrammarException(b.ToString()); } }
/// <summary> /// Add a grammar to the grammar list. /// </summary> /// <param name="grammar">The grammar.</param> protected internal void StoreGrammar(JSGFRuleGrammar grammar) { _grammars.Put(grammar.GetName(), grammar); }
public void Remove(JSGFRuleGrammar grammar) { String name = grammar.GetName(); _grammars.Remove(name); }