模板复写 modulename_canvas.html ( xoops themes )

不同模块选择不同的主题风格,在themes/modules/mod name 下创建canvas的模板,themes会自动筛选模块下的canvas如果不存在,在去找自身的canvas文件.

<{php}>
// Get language files
require_once(XOOPS_ROOT_PATH.'/language/'.$GLOBALS['xoopsConfig']['language'].'/user.php');


//If a module defines its own canvas template (located themes/theme/modules/dirname/canvas.html), take it; otherwise the default canvas (themes/theme/canvas.html) is used.
if(file_exists(XOOPS_ROOT_PATH."/themes/".$this->_tpl_vars["xoops_theme"]."/modules/".$this->_tpl_vars["xoops_dirname"]."/canvas.html")) {
    $this->assign("canvas_template", $this->_tpl_vars["xoops_theme"]."/modules/".$this->_tpl_vars["xoops_dirname"]."/canvas.html");
}else{
    $this->assign("canvas_template", $this->_tpl_vars["xoops_theme"]."/canvas.html");
}

//Defined an extra SMARTY variable $xoops_themeurl, which is identical to $xoops_imageurl, for literal consistence only.
$this->assign("xoops_themeurl", $this->_tpl_vars["xoops_url"]."/themes/".$this->_tpl_vars["xoops_theme"]);

//Defined an extra SMARTY variable $xoops_module_theme.
$this->assign("xoops_module_theme", $this->_tpl_vars["xoops_theme"]."/modules/".$this->_tpl_vars["xoops_dirname"]);

//If a module has its own css (located themes/theme/modules/dirname/style.css), append it to $xoops_module_header.
if(file_exists(XOOPS_ROOT_PATH."/themes/".$this->_tpl_vars["xoops_theme"]."/modules/".$this->_tpl_vars["xoops_dirname"]."/style.css")) {
    $this->assign("xoops_module_header",
                        $this->_tpl_vars["xoops_module_header"]."/n".
                        "<link rel=/"stylesheet/" type=/"text/css/" href=/"".$this->_tpl_vars["xoops_themeurl"]."/modules/".$this->_tpl_vars["xoops_dirname"]."/style.css/"/>/n"
                    );
}
<{/php}>

vtr_key.add(place_first); //以下zj300&200区别 /////////////////////////////////////////////////////////////////////////////////////////////////////////////// (16) // 往空LL1上放片不优 //if (env.test_idx.current == 127 && chain.chain.Count == 2) //{ // Console.WriteLine("~~~~~~~~~~~`"); //} List<String> other_ll_swap = new List<string>(); place_to_empty_ll = Tools.create_set_filter_null(chain.chain, chain_node=> (chain_node.node_type == NodeType.Place && chain_node.module.module_type == ModuleType.LL1) ? chain_node.module.module_name : null); LLGroup lg_temp = chain.chain[chain.chain.Count - 1].module.module_type == ModuleType.LL1 ? (LLGroup)chain.chain[chain.chain.Count - 1].module : null; double inferior_weight = 0.0; if (place_to_empty_ll.Count > 0) { LLGroup place_dest_ll = env.lgs1[place_to_empty_ll.First()]; LLGroup other_ll_group = Tools.create_list_filter_null(env.lgs1.Values, lgg_tt=> !string.Equals(lgg_tt.module_name, place_dest_ll.module_name) ? lgg_tt : null)[0]; other_ll_swap = Tools.create_list_filter_null(chain.chain, chain_node => (chain_node.node_type == NodeType.Swap && chain_node.module.module_name == other_ll_group.module_name) ? chain_node.module.module_name : null); List<Wafer> place_ws = Tools.create_set_filter_null(chain.chain, chain_node=> (chain_node.node_type == NodeType.Place && chain_node.module.module_type == ModuleType.LL1) ? chain_node.place_wafers : null).First(); // 另外一组LL Group可以做place或swap则不优 var intersectSetTemp = other_ll_group.ll_group_dict.Keys.Intersect(place_ws[0].ll_out.Keys).ToList(); if (place_dest_ll.empty() && !other_ll_group.empty() && intersectSetTemp.Count > 0 && (other_ll_group.mu_move_history.last_move() == null || env.elements[other_ll_group.mu_move_history.last_move().ModuleName].module_type == ModuleType.VTR1 ) //&& (env.lp_wafer.Keys.First().current_module().module_type != ModuleType.LP || env.lp_wafer.Keys.First().to_ll1_dest == null || env.lp_wafer.Keys.First().to_ll1_dest.group != other_ll_group) // 避免影响后续lp_wafer进片 ) //other_ll_group.valid_start_time_all <= place_dest_ll.valid_start_time_all { List<int> ll_could_swap_slot = new List<int>(); foreach (var step_module_info in place_ws[0].ll_out.Values) { int place_w_slot = step_module_info.SlotID; if (place_w_slot > 0) { List<Wafer> ll_current_wafers = other_ll_group.get_wafers(place_w_slot); if (ll_current_wafers == null ) // || (!ll_current_wafers[0].is_enter() && !has_two_load) { ll_could_swap_slot.Add(place_w_slot); } } else { foreach (var s in other_ll_group.accessible_slots_set) { if (other_ll_group.get_wafers(s) == null) //|| (!other_ll_group.get_wafers(s)[0].is_enter() && !has_two_load) { ll_could_swap_slot.Add(s); break; } } } if (ll_could_swap_slot.Count > 0) { inferior_weight += 1.0; break; } } } } // PM进片优于补齐LL bool is_empty_pms = false; List<Wafer> next_in_pm_wafers = Tools.create_list_filter_null(env.wafer_mid1, w => env.vtr1.ContainsKey(w.current_module_name()) && w.get_next_module_type().Contains(ModuleType.PM1) ? w.get_key_w() : null); next_in_pm_wafers.AddRange(ll_wafers_list); foreach (var ll_w in next_in_pm_wafers) { foreach (var pp in ll_w.all_pms) { if (env.elements[pp].empty()) { is_empty_pms = true; break; } } if (is_empty_pms) { break; } } // 尽快补齐LL最后一组wafer,让LL满载优先(避免出现从其他LL多次取片swap后再放到待出的LL上,提升LL转换效率) if (lg_temp != null && chain.chain[chain.chain.Count - 1].node_type == NodeType.Place && !lg_temp.empty() && lg_temp.opr_mode() == LLOprMode.Pump && chain.chain[chain.chain.Count - 1].place_slots != null) { int lg_slot = chain.chain[chain.chain.Count - 1].place_slots[0]; HashSet<int> other_slots = new HashSet<int>(lg_temp.accessible_slots_set); other_slots.Remove(lg_slot); bool lg_will_fill = Tools.all_of(other_slots, s => !lg_temp.empty(s) && lg_temp.get_wafers(s) != null && lg_temp.get_wafers(s)[0].get_next_module_type().Contains(ModuleType.ATR)); //bool lg_not_empty = Tools.any_of(other_slots, s => !lg_temp.empty(s) && lg_temp.get_wafers(s) != null && lg_temp.get_wafers(s)[0].get_next_module_type().Contains(ModuleType.ATR)); if (lg_will_fill && lg_temp.empty(lg_slot) && (!is_empty_pms //|| (chain.chain.Count() > 1 && chain.chain[1].place_wafers[0].sequence.pm_triple_neck_time < chain.chain[1].place_wafers[0].sequence.ll_triple_neck_time - 0.01) // 20241014todo )) { //inferior_weight -= max_length_vtr_chain_list - chain.chain.Count; inferior_weight -= 1 - other_ll_swap.Count(); } //else if (lg_not_empty && lg_temp.empty(lg_slot) // && (chain.chain.Count() > 1 && chain.chain[1].place_wafers[0].sequence.pm_triple_neck_time < chain.chain[1].place_wafers[0].sequence.ll_triple_neck_time - 0.01) // ) //{ // inferior_weight -= 1 - other_ll_swap.Count(); //} } //20241014Todo //else if (!is_empty_pms && lg_temp != null && chain.chain[chain.chain.Count - 1].node_type == NodeType.Place && lg_temp.empty() // && lg_temp.opr_mode() != LLOprMode.Pump && chain.chain[chain.chain.Count - 1].place_slots != null // && chain.chain.Count == 2 // ) //{ // int lg_slot = chain.chain[chain.chain.Count - 1].place_slots[0]; // HashSet<int> other_slots = new HashSet<int>(lg_temp.accessible_slots_set); // other_slots.Remove(lg_slot); // bool lg_not_empty = Tools.any_of(other_slots, s => !lg_temp.empty(s) && lg_temp.get_wafers(s) != null && lg_temp.get_wafers(s)[0].get_next_module_type().Contains(ModuleType.ATR)); // if (lg_temp.empty(lg_slot) // && (chain.chain.Count() > 1 && chain.chain[1].place_wafers[0].sequence.pm_triple_neck_time < chain.chain[1].place_wafers[0].sequence.ll_triple_neck_time - 0.01) // ) // { // inferior_weight -= 1 - other_ll_swap.Count(); // } //} //// 20241014 Todo:VTR持片等待PM做Clean不优 //if (chain.chain.Count == 2 && chain.chain[0].node_type == NodeType.Swap && chain.chain[1].node_type == NodeType.Place && // Tools.any_of(chain.chain, ch => ch.clean_list != null && ch.clean_list.Count > 0 && ch.clean_time > 0)) //{ // inferior_weight += Tools.create_set_filter_null(chain.chain, ch => ch.clean_list != null && ch.clean_list.Count > 0 && ch.clean_time > 0 ? null : ch).Count; //} // 向lp_wafer的dest_ll放片导致不能及时进片不优 // if (lg_temp != null && env.lp_wafer.Keys.First().current_module().module_type == ModuleType.LP && env.lp_wafer.Keys.First().to_ll1_dest != null && env.lp_wafer.Keys.First().to_ll1_dest.group == lg_temp) // { // inferior_weight += 1.0; //} vtr_key.add(inferior_weight); //以上zj300&200区别 /////////////////////////////////////////////////////////////////////////////////////////////////////////////// (15) // 进料优先, ll=>pm 比 pm=>ll优先 var priority_flag = 0; #if true if (vtr.module_type == ModuleType.VTR1 && chain.chain.Count() > 1 && vtr_first_node.node_type == NodeType.Pick && vtr_first_node.module.module_type == ModuleType.PM1 && chain.chain[1].module.module_type == ModuleType.LL1) #endif { if (!vtr_first_node.pick_wafers[0].has_time_constraint || vtr_first_node.pick_wafers[0].get_residency_constraint(vtr_first_node.pick_wafers[0].current_step_id(), vtr_first_node.pick_wafers[0].current_module_name()) >= 30) { if (Tools.any_of(vtr_chain_list, chain_t => chain_t.first_node().module.module_type == ModuleType.LL1 && chain_t.chain.Count() > 1 && (chain_t.chain[1].module == vtr_first_node.module || chain_t.chain[chain_t.chain.Count-1].module.module_type==ModuleType.PM1) && (chain_t.chain_end > 0 || chain_t.chain.Count() > 2) && (chain_t.chain[1].start < chain.chain[1].end || chain.chain[1].end < 0) && NodeTypeExtensions.places.Contains(chain_t.chain[1].node_type) // 避免双pick场景 // && !chain_t.first_node().pick_wafers.get(0).has_time_constraint //&& ((chain_t.chain[1].place_wafers[0].sequence.pm_triple_neck_time > chain_t.chain[1].place_wafers[0].sequence.ll_triple_neck_time + 0.01) || !chain_t.chain[1].place_wafers[0].sequence.ll_diff) // 避免短工艺片子仍在PM做swap不优,20241014todo )) { priority_flag = 1; // 不优 } } else { #if true foreach (var chain_t in vtr_chain_list) { //double residency_constraint = vtr_first_node.pick_wafers[0].route_recipe[vtr_first_node.pick_wafers[0].current_step_id()][vtr_first_node.pick_wafers[0].current_module_name()].ResidencyConstraint; //get_residency_constraint(this.current_step_id(), this.current_module_name()); // 有驻留时间,并且驻留时间小于算法规划pick time if (chain_t.first_node().pick_wafers[0].has_time_constraint// && chain_t.first_node().pick_wafers[0].not_swap_at_pm() && chain_t.chain.Count() > 1 && chain_t.chain[1].module.module_type == ModuleType.LL1 && (chain_t.chain_end > 0 || chain_t.chain.Count() > 2) && (chain_t.chain[1].start < chain.chain[1].end || chain.chain[1].end < 0) && NodeTypeExtensions.places.Contains(chain_t.chain[1].node_type) // 避免双pick场景 && Tools.any_of(chain_t.chain, ch_t => ch_t.node_type == NodeType.Swap && ch_t.module != vtr_first_node.module && vtr_first_node.pick_wafers[0].OverResidencyTime(ch_t.module_start) > 0) ) // 避免短工艺片子仍在PM做swap不优,20241014todo { priority_flag = -1; // 不优 break; } // 无驻留时间,或者驻留时间设置很大 else if (chain_t.first_node().module.module_type == ModuleType.PM1 && chain_t.chain.Count() > 1 && chain_t.chain[1].module == vtr_first_node.module && (chain_t.chain_end > 0 || chain_t.chain.Count() > 2) && (chain_t.chain[1].start < chain.chain[1].end || chain.chain[1].end < 0) && NodeTypeExtensions.places.Contains(chain_t.chain[1].node_type) // 避免双pick场景 && Tools.any_of(chain_t.chain, ch_t => ch_t.node_type == NodeType.Swap && ch_t.module == vtr_first_node.module && (!chain_t.first_node().pick_wafers[0].has_time_constraint || vtr_first_node.pick_wafers[0].OverResidencyTime(ch_t.module_start) <= 0) )) { priority_flag = -1; // 较优 break; } // 有驻留时间,但是工艺时间很大,可以满足ll 优先进片,然后 vtr 手 再次从pm pick片子 //else if (chain_t.first_node().pick_wafers[0].has_time_constraint// && chain_t.first_node().pick_wafers[0].not_swap_at_pm() // && chain_t.chain.Count() > 1 && chain_t.chain[1].module.module_type == ModuleType.LL1 && (chain_t.chain_end > 0 || chain_t.chain.Count() > 2) && // (chain_t.chain[1].start < chain.chain[1].end || chain.chain[1].end < 0) // && NodeTypeExtensions.places.Contains(chain_t.chain[1].node_type) // 避免双pick场景 // && Tools.any_of(chain_t.chain, ch_t => ch_t.node_type == NodeType.Swap && ch_t.module == vtr_first_node.module && vtr_first_node.pick_wafers[0].OverResidencyTime(ch_t.module_start) > 0) // ) //{ //} } #endif } } vtr_key.add(priority_flag); /////////////////////////////////////////////////////////////////////////////////////////////////////////////// (22) // 如果违反ProcType, 那么不优 var proc_type_flag = 0; if (vtr_end_node.node_type == NodeType.Place && chain.chain_end > 0 && vtr_end_node.module_start - vtr_end_node.module.valid_start() > 0.01 && vtr_end_node.module is PM pmt) { var pm_move = pmt.process_move_list.last_move(); if ( pm_move != null && pm_move.CleanType == CleanType.ChamberShortClean && Tools.any_of(vtr_chain_list, c => { var end_node_c = c.end_node(); return c.chain_end > 0 && end_node_c.module_start + 0.001 < vtr_end_node.module_start && end_node_c.module == vtr_end_node.module && end_node_c.place_wafers[0].get_key_w() == vtr_end_node.place_wafers[0].get_key_w(); }) ) { proc_type_flag = 1; } } vtr_key.add(proc_type_flag); /////////////////////////////////////////////////////////////////////////////////////////////////////////////// (23) // 单片优先选择单片的PM vtr_key.add(single_flag);
最新发布
08-22
# VTR选择链逻辑分析(续) ## LL放置优化和优先级处理逻辑 这段代码实现了机器人调度系统中复杂的LL(Load Lock)放置优化和优先级处理逻辑: ```csharp // 往空LL1上放片的不优权重计算 List<String> other_ll_swap = new List<string>(); place_to_empty_ll = Tools.create_set_filter_null(chain.chain, chain_node => (chain_node.node_type == NodeType.Place && chain_node.module.module_type == ModuleType.LL1) ? chain_node.module.module_name : null); LLGroup lg_temp = chain.chain[chain.chain.Count - 1].module.module_type == ModuleType.LL1 ? (LLGroup)chain.chain[chain.chain.Count - 1].module : null; double inferior_weight = 0.0; if (place_to_empty_ll.Count > 0) { LLGroup place_dest_ll = env.lgs1[place_to_empty_ll.First()]; LLGroup other_ll_group = Tools.create_list_filter_null(env.lgs1.Values, lgg_tt => !string.Equals(lgg_tt.module_name, place_dest_ll.module_name) ? lgg_tt : null)[0]; other_ll_swap = Tools.create_list_filter_null(chain.chain, chain_node => (chain_node.node_type == NodeType.Swap && chain_node.module.module_name == other_ll_group.module_name) ? chain_node.module.module_name : null); List<Wafer> place_ws = Tools.create_set_filter_null(chain.chain, chain_node => (chain_node.node_type == NodeType.Place && chain_node.module.module_type == ModuleType.LL1) ? chain_node.place_wafers : null).First(); // 检查另一组LL Group是否可以做place或swap var intersectSetTemp = other_ll_group.ll_group_dict.Keys.Intersect(place_ws[0].ll_out.Keys).ToList(); if (place_dest_ll.empty() && !other_ll_group.empty() && intersectSetTemp.Count > 0 && (other_ll_group.mu_move_history.last_move() == null || env.elements[other_ll_group.mu_move_history.last_move().ModuleName].module_type == ModuleType.VTR1)) { List<int> ll_could_swap_slot = new List<int>(); foreach (var step_module_info in place_ws[0].ll_out.Values) { int place_w_slot = step_module_info.SlotID; if (place_w_slot > 0) { List<Wafer> ll_current_wafers = other_ll_group.get_wafers(place_w_slot); if (ll_current_wafers == null) { ll_could_swap_slot.Add(place_w_slot); } } else { foreach (var s in other_ll_group.accessible_slots_set) { if (other_ll_group.get_wafers(s) == null) { ll_could_swap_slot.Add(s); break; } } } if (ll_could_swap_slot.Count > 0) { inferior_weight += 1.0; break; } } } } ``` ## 代码解释 1. **空LL1放置优化**: - 检测当前链是否包含向LL1放置操作 - 获取目标LL组和其他LL组 - 计算放置到空LL1的不优权重 2. **LL组比较逻辑**: - 如果目标LL为空但其他LL不为空 - 且其他LL可以放置当前晶圆 - 则增加不优权重 3. **PM进片优先级**: ```csharp bool is_empty_pms = false; List<Wafer> next_in_pm_wafers = Tools.create_list_filter_null(env.wafer_mid1, w => env.vtr1.ContainsKey(w.current_module_name()) && w.get_next_module_type().Contains(ModuleType.PM1) ? w.get_key_w() : null); next_in_pm_wafers.AddRange(ll_wafers_list); foreach (var ll_w in next_in_pm_wafers) { foreach (var pp in ll_w.all_pms) { if (env.elements[pp].empty()) { is_empty_pms = true; break; } } if (is_empty_pms) { break; } } ``` 4. **LL满载优化**: ```csharp if (lg_temp != null && chain.chain[chain.chain.Count - 1].node_type == NodeType.Place && !lg_temp.empty() && lg_temp.opr_mode() == LLOprMode.Pump && chain.chain[chain.chain.Count - 1].place_slots != null) { int lg_slot = chain.chain[chain.chain.Count - 1].place_slots[0]; HashSet<int> other_slots = new HashSet<int>(lg_temp.accessible_slots_set); other_slots.Remove(lg_slot); bool lg_will_fill = Tools.all_of(other_slots, s => !lg_temp.empty(s) && lg_temp.get_wafers(s) != null && lg_temp.get_wafers(s)[0].get_next_module_type().Contains(ModuleType.ATR)); if (lg_will_fill && lg_temp.empty(lg_slot) && !is_empty_pms) { inferior_weight -= 1 - other_ll_swap.Count(); } } ``` 5. **进料优先级处理**: ```csharp var priority_flag = 0; if (vtr.module_type == ModuleType.VTR1 && chain.chain.Count() > 1 && vtr_first_node.node_type == NodeType.Pick && vtr_first_node.module.module_type == ModuleType.PM1 && chain.chain[1].module.module_type == ModuleType.LL1) { if (!vtr_first_node.pick_wafers[0].has_time_constraint || vtr_first_node.pick_wafers[0].get_residency_constraint(...) >= 30) { if (Tools.any_of(vtr_chain_list, chain_t => ...)) { priority_flag = 1; // 不优 } } else { foreach (var chain_t in vtr_chain_list) { // 处理有驻留时间约束的情况 // 处理无驻留时间或工艺时间足够的情况 } } } ``` ## 代码分析总结 这段代码实现了机器人调度系统中复杂的LL放置优化和优先级处理逻辑: 1. **LL放置优化**: - 检测向空LL1放置晶圆的情况 - 比较其他LL组的可用性 - 根据情况动态调整不优权重 2. **PM进片优先级**: - 检查是否有需要进入PM的晶圆 - 如果有空闲PM,则增加LL放置的不优权重 3. **LL满载优化**: - 检查LL是否即将满载 - 如果即将满载且PM不空闲,则减少不优权重 - 确保LL满载时优先处理 4. **进料优先级处理**: - 区分PM到LL和LL到PM的操作优先级 - 考虑晶圆的驻留时间约束 - 根据工艺要求动态调整优先级 5. **其他优化**: - 处理违反ProcType的情况 - 处理单片优先选择单片PM的情况 - 避免影响后续进片的情况 这段代码展示了如何在复杂的生产环境中,根据多种因素动态调整机器人的操作顺序,以优化LL使用效率并提高整体生产效率。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值