[
https://issues.apache.org/jira/browse/LANG-1641?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=17276281#comment-17276281
]
Michael Buck commented on LANG-1641:
------------------------------------
See PR here: [https://github.com/apache/commons-lang/pull/703]
> Over Stack Issue
> ----------------
>
> Key: LANG-1641
> URL: https://issues.apache.org/jira/browse/LANG-1641
> Project: Commons Lang
> Issue Type: Bug
> Components: lang.time.*
> Affects Versions: 3.7
> Reporter: Xia Yun
> Priority: Major
> Time Spent: 20m
> Remaining Estimate: 0h
>
> {code:java}
> //this is the demo
> package com.wcs233;
> import java.util.Date;
> import java.util.TimeZone;
> import org.apache.commons.lang3.time.DateFormatUtils;
> import org.apache.commons.lang3.time.FastTimeZone;
> public class GmtTimeZoneIssue {
> public static void main(String[] args) {
> final String timeZoneString = "GMT+7:00";
> final String ISO8601_DATE_FORMAT = "yyyy-MM-dd'T'HH:mm:ssZZ";
> for (int i = 0; i < 100; i++) {
> Date date = new Date();
> TimeZone timeZone = FastTimeZone.getTimeZone(timeZoneString);
> String dateString = DateFormatUtils.format(date,
> ISO8601_DATE_FORMAT, timeZone);
> System.out.println(dateString);
> }
> }
> }{code}
> when running the code above , there is over stack risk
> 1. When invoking FastTimeZone.getTimeZone(timeZoneString), a new GmtTimeZone
> will be created
> {code:java}
> GmtTimeZone(final boolean negate, final int hours, final int minutes) {
> if (hours >= HOURS_PER_DAY) {
> throw new IllegalArgumentException(hours + " hours out of range");
> }
> if (minutes >= MINUTES_PER_HOUR) {
> throw new IllegalArgumentException(minutes + " minutes out of
> range");
> }
> final int milliseconds = (minutes + (hours * MINUTES_PER_HOUR)) *
> MILLISECONDS_PER_MINUTE;
> offset = negate ? -milliseconds : milliseconds;
> zoneId = twoDigits(
> twoDigits(new StringBuilder(9).append("GMT").append(negate ? '-'
> : '+'), hours)
> .append(':'), minutes).toString();
> }
> {code}
> the every GmtTimeZone instance , the zoneIds instance are different , even
> through the values are the same.
> 2. When invoking DateFormatUtils.format(), there is a ConCurrentHashMap in
> FormatCache with key is MultipartKey. when invoking
> FormatCache.getInstance(), first get from cInstanceCache, if value is null,
> putIfAbsent, but because GmtTimeZone instances are different, when invoking
> GmtTimeZone.equals, the logic is
> {code:java}
> @Override
> public boolean equals(final Object other) {
> if (!(other instanceof GmtTimeZone)) {
> return false;
> }
> return zoneId == ((GmtTimeZone) other).zoneId;
> }
> {code}
> every zoneId address are different so, equals function return false, but
> actually the zoneId values are the same.
> so FastDateFormat will be put into cInstanceCache in FormatCache again and
> again, which will increase the capability of the map, and cause over stack
> risk, also, it will cause application run much slower.
--
This message was sent by Atlassian Jira
(v8.3.4#803005)