import resource
import sys
from c2po import log
MODULE_CODE = "UTIL"
def format_bytes(bytes: int) -> str:
if bytes < 1024:
return f"{bytes} bytes"
elif bytes < 1024 * 1024:
return f"{bytes / 1024:.2f} KB"
elif bytes < 1024 * 1024 * 1024:
return f"{bytes / 1024 / 1024:.2f} MB"
else:
return f"{bytes / 1024 / 1024 / 1024:.2f} GB"
def get_rusage_time() -> float:
rusage_self = resource.getrusage(resource.RUSAGE_SELF)
rusage_child = resource.getrusage(resource.RUSAGE_CHILDREN)
return (
rusage_self.ru_utime
+ rusage_child.ru_utime
+ rusage_self.ru_stime
+ rusage_child.ru_stime
)
def set_max_memory(bytes: int) -> None:
if sys.platform == "darwin":
log.debug(
MODULE_CODE,
1,
"macOS does not support setrlimit for RLIMIT_AS, ignoring max memory limit",
)
return
log.debug(MODULE_CODE, 1, f"Setting max memory to {format_bytes(bytes)}")
try:
resource.setrlimit(resource.RLIMIT_AS, (bytes, resource.RLIM_INFINITY))
except ValueError:
log.warning(
MODULE_CODE,
"Failed to set max memory limit, provided limit is likely over current hard limit or OS does not support setrlimit for RLIMIT_AS",
)
except OverflowError:
log.warning(
MODULE_CODE,
"Failed to set max memory limit, provided limit is likely over current hard limit or OS does not support setrlimit for RLIMIT_AS",
)
def set_max_memory_offset(bytes: int) -> None:
if bytes <= 0:
return
rusage_self = resource.getrusage(resource.RUSAGE_SELF)
rusage_child = resource.getrusage(resource.RUSAGE_CHILDREN)
current_memory = rusage_self.ru_maxrss + rusage_child.ru_maxrss
if sys.platform == "darwin":
current_memory = current_memory // 1024
log.debug(MODULE_CODE, 1, f"Current memory usage: {format_bytes(current_memory * 1024)}")
new_memory = bytes + current_memory
set_max_memory(new_memory)