diff options
| author | Matthew Barth <msbarth@us.ibm.com> | 2011-09-29 15:42:30 -0500 |
|---|---|---|
| committer | MATTHEW S. BARTH <msbarth@us.ibm.com> | 2011-10-10 15:51:19 -0500 |
| commit | 8c062af8b6bd50a59823c7ec430ec5fc019052d2 (patch) | |
| tree | dbe0625a3024a3737ddfa5d32634ce8225fda991 /src/kernel/blockmsghdlr.C | |
| parent | 4de170997eee6244b2091bb8bf065ae2da1396d7 (diff) | |
| download | blackbird-hostboot-8c062af8b6bd50a59823c7ec430ec5fc019052d2.tar.gz blackbird-hostboot-8c062af8b6bd50a59823c7ec430ec5fc019052d2.zip | |
Flush/Release/Evict pages functionality
Change-Id: Ic0bb4122164e11f6d13e6850abf8ae9bd32caea2
Reviewed-on: http://gfw160.austin.ibm.com:8080/gerrit/393
Tested-by: Jenkins Server
Reviewed-by: MATTHEW S. BARTH <msbarth@us.ibm.com>
Diffstat (limited to 'src/kernel/blockmsghdlr.C')
| -rw-r--r-- | src/kernel/blockmsghdlr.C | 73 |
1 files changed, 72 insertions, 1 deletions
diff --git a/src/kernel/blockmsghdlr.C b/src/kernel/blockmsghdlr.C index cf1683cab..fc49ae89d 100644 --- a/src/kernel/blockmsghdlr.C +++ b/src/kernel/blockmsghdlr.C @@ -22,8 +22,9 @@ // IBM_PROLOG_END #include <kernel/blockmsghdlr.H> #include <kernel/block.H> +#include <kernel/pagemgr.H> -MessageHandler::HandleResult BlockMsgHdlr::handleResponse( +MessageHandler::HandleResult BlockReadMsgHdlr::handleResponse( msg_sys_types_t i_type, void* i_key, task_t* i_task, int i_rc) { if (i_rc != 0) @@ -41,3 +42,73 @@ MessageHandler::HandleResult BlockMsgHdlr::handleResponse( return SUCCESS; } } + +MessageHandler::HandleResult BlockWriteMsgHdlr::handleResponse( + msg_sys_types_t i_type, void* i_key, task_t* i_task, int i_rc) +{ + //Default to indicate nothing specific has been done for this response. + MessageHandler::HandleResult l_result = UNHANDLED_RC; + if (i_rc != 0) + { + //Request default behavior of resume/kill task based on rc. + return l_result; + } + //Find the virtual address to page address mapping to know which page + //address to release since only the virtual address is available on the msg + PageAddrNode* l_paNode = iv_va2paList.find(i_key); + if (l_paNode) + { + l_result = SUCCESS; + //Complete page removal and remove list entry + PageManager::freePage(reinterpret_cast<void*>(l_paNode->pageAddr)); + iv_va2paList.erase(l_paNode); + delete l_paNode; + } + //Not handling a reponse from kernel + if (i_task != NULL) + { + //Find the task's msg count to know how many messages were sent + //to remove pages and whether to continue deferring the task or not + TaskMsgNode* l_tmNode = iv_msgGrpList.find(i_task); + if (l_tmNode) + { + //Last message for the given task + if (l_tmNode->msgCount == 1 && + (l_tmNode->next == NULL && l_tmNode->prev == NULL)) + { + l_result = SUCCESS; + iv_msgGrpList.erase(l_tmNode); + delete l_tmNode; + } + else + { + l_result = CONTINUE_DEFER; + l_tmNode->msgCount--; + } + } + } + + return l_result; +} + +void BlockWriteMsgHdlr::incMsgCount(task_t* i_task) +{ + TaskMsgNode* l_tmNode = iv_msgGrpList.find(i_task); + if (l_tmNode == NULL) + { + //Add task to list and set message count to 1 + l_tmNode = new TaskMsgNode(); + l_tmNode->key = i_task; + l_tmNode->msgCount = 0; + iv_msgGrpList.insert(l_tmNode); + } + l_tmNode->msgCount++; +} + +void BlockWriteMsgHdlr::addVirtAddr(void* i_vaddr,uint64_t i_pgAddr) +{ + PageAddrNode* l_paNode = new PageAddrNode(); + l_paNode->key = i_vaddr; + l_paNode->pageAddr = i_pgAddr; + iv_va2paList.insert(l_paNode); +} |

