@@ -133,10 +133,7 @@ public function __construct(
133133 public function get ($ app , $ lang = null , $ locale = null ) {
134134 return new LazyL10N (function () use ($ app , $ lang , $ locale ) {
135135 $ app = \OC_App::cleanAppId ($ app );
136- if ($ lang !== null ) {
137- $ lang = str_replace (['\0 ' , '/ ' , '\\' , '.. ' ], '' , $ lang );
138- }
139-
136+ $ lang = $ this ->cleanLanguage ($ lang );
140137 $ forceLang = $ this ->config ->getSystemValue ('force_language ' , false );
141138 if (is_string ($ forceLang )) {
142139 $ lang = $ forceLang ;
@@ -169,6 +166,29 @@ public function get($app, $lang = null, $locale = null) {
169166 });
170167 }
171168
169+ /**
170+ * Remove some invalid characters before using a string as a language
171+ *
172+ * @psalm-taint-escape callable
173+ * @psalm-taint-escape cookie
174+ * @psalm-taint-escape file
175+ * @psalm-taint-escape has_quotes
176+ * @psalm-taint-escape header
177+ * @psalm-taint-escape html
178+ * @psalm-taint-escape include
179+ * @psalm-taint-escape ldap
180+ * @psalm-taint-escape shell
181+ * @psalm-taint-escape sql
182+ * @psalm-taint-escape unserialize
183+ */
184+ private function cleanLanguage (?string $ lang ): ?string {
185+ if ($ lang === null ) {
186+ return null ;
187+ }
188+ $ lang = preg_replace ('/[^a-zA-Z0-9.;,=-]/ ' , '' , $ lang );
189+ return str_replace ('.. ' , '' , $ lang );
190+ }
191+
172192 /**
173193 * Find the best language
174194 *
@@ -478,7 +498,7 @@ public function localeExists($locale) {
478498 * @throws LanguageNotFoundException
479499 */
480500 private function getLanguageFromRequest (?string $ app = null ): string {
481- $ header = $ this ->request ->getHeader ('ACCEPT_LANGUAGE ' );
501+ $ header = $ this ->cleanLanguage ( $ this -> request ->getHeader ('ACCEPT_LANGUAGE ' ) );
482502 if ($ header !== '' ) {
483503 $ available = $ this ->findAvailableLanguages ($ app );
484504
0 commit comments