From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-11.1 required=3.0 tests=BAYES_00,DKIM_SIGNED, DKIM_VALID,DKIM_VALID_AU,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH, MAILING_LIST_MULTI,MIME_BASE64_TEXT,SIGNED_OFF_BY,SPF_HELO_NONE,SPF_PASS, UNPARSEABLE_RELAY,URIBL_BLOCKED,USER_AGENT_GIT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 30E0AC2D0A3 for ; Mon, 26 Oct 2020 08:19:24 +0000 (UTC) Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by mail.kernel.org (Postfix) with ESMTP id C9D2A20878 for ; Mon, 26 Oct 2020 08:19:23 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (1024-bit key) header.d=mediatek.com header.i=@mediatek.com header.b="ovn6pY5E" Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1771250AbgJZITV (ORCPT ); Mon, 26 Oct 2020 04:19:21 -0400 Received: from mailgw02.mediatek.com ([210.61.82.184]:54768 "EHLO mailgw02.mediatek.com" rhost-flags-OK-FAIL-OK-FAIL) by vger.kernel.org with ESMTP id S1736795AbgJZITU (ORCPT ); Mon, 26 Oct 2020 04:19:20 -0400 X-UUID: 9c217e4e00ed4016bac869981d3b571c-20201026 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=mediatek.com; s=dk; h=Content-Transfer-Encoding:Content-Type:MIME-Version:References:In-Reply-To:Message-ID:Date:Subject:CC:To:From; bh=s89f08KvBYl1d0htgXzsoi2iHSJgKoDYNXWWA86n02U=; b=ovn6pY5E+F82H1yQbNWyr8o2VmqfzwIx3CU48BW9rbg3XC/GxG56ith9s1UJI1RU3myCJYrusWgJvFE40+PzRC9r499Wnq/+g8Vvi35C9saIltpdIfV1sIyMDsE05ndGHLBdgHer92liH9bYFsLOIPdB9KjzHq27zV6bIcRgVjU=; X-UUID: 9c217e4e00ed4016bac869981d3b571c-20201026 Received: from mtkcas11.mediatek.inc [(172.21.101.40)] by mailgw02.mediatek.com (envelope-from ) (Cellopoint E-mail Firewall v4.1.14 Build 0819 with TLSv1.2 ECDHE-RSA-AES256-SHA384 256/256) with ESMTP id 1006871668; Mon, 26 Oct 2020 16:19:15 +0800 Received: from mtkcas08.mediatek.inc (172.21.101.126) by mtkmbs07n2.mediatek.inc (172.21.101.141) with Microsoft SMTP Server (TLS) id 15.0.1497.2; Mon, 26 Oct 2020 16:19:14 +0800 Received: from mtkswgap22.mediatek.inc (172.21.77.33) by mtkcas08.mediatek.inc (172.21.101.73) with Microsoft SMTP Server id 15.0.1497.2 via Frontend Transport; Mon, 26 Oct 2020 16:19:13 +0800 From: Hector Yuan To: , , , Rob Herring , Sudeep Holla , "Rafael J. Wysocki" , Viresh Kumar , Maxime Ripard , Santosh Shilimkar , Amit Kucheria , Stephen Boyd , Ulf Hansson , Dave Gerlach , Florian Fainelli , Robin Murphy , Lorenzo Pieralisi , CC: , , Subject: [PATCH v8 1/3] cpufreq: mediatek-hw: Add support for CPUFREQ HW Date: Mon, 26 Oct 2020 16:19:07 +0800 Message-ID: <1603700349-5922-2-git-send-email-hector.yuan@mediatek.com> X-Mailer: git-send-email 1.7.9.5 In-Reply-To: <1603700349-5922-1-git-send-email-hector.yuan@mediatek.com> References: <1603700349-5922-1-git-send-email-hector.yuan@mediatek.com> MIME-Version: 1.0 Content-Type: text/plain X-MTK: N Content-Transfer-Encoding: base64 Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org RnJvbTogIkhlY3Rvci5ZdWFuIiA8aGVjdG9yLnl1YW5AbWVkaWF0ZWsuY29tPg0KDQpBZGQgY3B1 ZnJlcSBIVyBzdXBwb3J0Lg0KDQpTaWduZWQtb2ZmLWJ5OiBIZWN0b3IuWXVhbiA8aGVjdG9yLnl1 YW5AbWVkaWF0ZWsuY29tPg0KLS0tDQogZHJpdmVycy9jcHVmcmVxL0tjb25maWcuYXJtICAgICAg ICAgICB8ICAgMTIgKysNCiBkcml2ZXJzL2NwdWZyZXEvTWFrZWZpbGUgICAgICAgICAgICAgIHwg ICAgMSArDQogZHJpdmVycy9jcHVmcmVxL21lZGlhdGVrLWNwdWZyZXEtaHcuYyB8ICAzNDMgKysr KysrKysrKysrKysrKysrKysrKysrKysrKysrKysrDQogMyBmaWxlcyBjaGFuZ2VkLCAzNTYgaW5z ZXJ0aW9ucygrKQ0KIGNyZWF0ZSBtb2RlIDEwMDY0NCBkcml2ZXJzL2NwdWZyZXEvbWVkaWF0ZWst Y3B1ZnJlcS1ody5jDQoNCmRpZmYgLS1naXQgYS9kcml2ZXJzL2NwdWZyZXEvS2NvbmZpZy5hcm0g Yi9kcml2ZXJzL2NwdWZyZXEvS2NvbmZpZy5hcm0NCmluZGV4IGNiNzJmYjUuLmI5ZDE3YzUgMTAw NjQ0DQotLS0gYS9kcml2ZXJzL2NwdWZyZXEvS2NvbmZpZy5hcm0NCisrKyBiL2RyaXZlcnMvY3B1 ZnJlcS9LY29uZmlnLmFybQ0KQEAgLTEyMyw2ICsxMjMsMTggQEAgY29uZmlnIEFSTV9NRURJQVRF S19DUFVGUkVRDQogCWhlbHANCiAJICBUaGlzIGFkZHMgdGhlIENQVUZyZXEgZHJpdmVyIHN1cHBv cnQgZm9yIE1lZGlhVGVrIFNvQ3MuDQogDQorY29uZmlnIEFSTV9NRURJQVRFS19DUFVGUkVRX0hX DQorCXRyaXN0YXRlICJNZWRpYVRlayBDUFVGcmVxIEhXIGRyaXZlciINCisJZGVwZW5kcyBvbiBB UkNIX01FRElBVEVLIHx8IENPTVBJTEVfVEVTVA0KKwlkZWZhdWx0IG0NCisJaGVscA0KKwkgIFN1 cHBvcnQgZm9yIHRoZSBDUFVGcmVxIEhXIGRyaXZlci4NCisJICBTb21lIE1lZGlhVGVrIGNoaXBz ZXRzIGhhdmUgYSBIVyBlbmdpbmUgdG8gb2ZmbG9hZCB0aGUgc3RlcHMNCisJICBuZWNlc3Nhcnkg Zm9yIGNoYW5naW5nIHRoZSBmcmVxdWVuY3kgb2YgdGhlIENQVXMuIEZpcm13YXJlIGxvYWRlZA0K KwkgIGluIHRoaXMgZW5naW5lIGV4cG9zZXMgYSBwcm9ncmFtbWluZyBpbnRlcmZhY2UgdG8gdGhl IE9TLg0KKwkgIFRoZSBkcml2ZXIgaW1wbGVtZW50cyB0aGUgY3B1ZnJlcSBpbnRlcmZhY2UgZm9y IHRoaXMgSFcgZW5naW5lLg0KKwkgIFNheSBZIGlmIHlvdSB3YW50IHRvIHN1cHBvcnQgQ1BVRnJl cSBIVy4NCisNCiBjb25maWcgQVJNX09NQVAyUExVU19DUFVGUkVRDQogCWJvb2wgIlRJIE9NQVAy KyINCiAJZGVwZW5kcyBvbiBBUkNIX09NQVAyUExVUw0KZGlmZiAtLWdpdCBhL2RyaXZlcnMvY3B1 ZnJlcS9NYWtlZmlsZSBiL2RyaXZlcnMvY3B1ZnJlcS9NYWtlZmlsZQ0KaW5kZXggZjFiN2UzZC4u ZmZjNjFjZCAxMDA2NDQNCi0tLSBhL2RyaXZlcnMvY3B1ZnJlcS9NYWtlZmlsZQ0KKysrIGIvZHJp dmVycy9jcHVmcmVxL01ha2VmaWxlDQpAQCAtNTcsNiArNTcsNyBAQCBvYmotJChDT05GSUdfQVJN X0lNWDZRX0NQVUZSRVEpCQkrPSBpbXg2cS1jcHVmcmVxLm8NCiBvYmotJChDT05GSUdfQVJNX0lN WF9DUFVGUkVRX0RUKQkrPSBpbXgtY3B1ZnJlcS1kdC5vDQogb2JqLSQoQ09ORklHX0FSTV9LSVJL V09PRF9DUFVGUkVRKQkrPSBraXJrd29vZC1jcHVmcmVxLm8NCiBvYmotJChDT05GSUdfQVJNX01F RElBVEVLX0NQVUZSRVEpCSs9IG1lZGlhdGVrLWNwdWZyZXEubw0KK29iai0kKENPTkZJR19BUk1f TUVESUFURUtfQ1BVRlJFUV9IVykJKz0gbWVkaWF0ZWstY3B1ZnJlcS1ody5vDQogb2JqLSQoQ09O RklHX01BQ0hfTVZFQlVfVjcpCQkrPSBtdmVidS1jcHVmcmVxLm8NCiBvYmotJChDT05GSUdfQVJN X09NQVAyUExVU19DUFVGUkVRKQkrPSBvbWFwLWNwdWZyZXEubw0KIG9iai0kKENPTkZJR19BUk1f UFhBMnh4X0NQVUZSRVEpCSs9IHB4YTJ4eC1jcHVmcmVxLm8NCmRpZmYgLS1naXQgYS9kcml2ZXJz L2NwdWZyZXEvbWVkaWF0ZWstY3B1ZnJlcS1ody5jIGIvZHJpdmVycy9jcHVmcmVxL21lZGlhdGVr LWNwdWZyZXEtaHcuYw0KbmV3IGZpbGUgbW9kZSAxMDA2NDQNCmluZGV4IDAwMDAwMDAuLjNhZjM2 YjANCi0tLSAvZGV2L251bGwNCisrKyBiL2RyaXZlcnMvY3B1ZnJlcS9tZWRpYXRlay1jcHVmcmVx LWh3LmMNCkBAIC0wLDAgKzEsMzQzIEBADQorLy8gU1BEWC1MaWNlbnNlLUlkZW50aWZpZXI6IEdQ TC0yLjANCisvKg0KKyAqIENvcHlyaWdodCAoYykgMjAyMCBNZWRpYVRlayBJbmMuDQorICovDQor DQorI2luY2x1ZGUgPGxpbnV4L2JpdGZpZWxkLmg+DQorI2luY2x1ZGUgPGxpbnV4L2NwdWZyZXEu aD4NCisjaW5jbHVkZSA8bGludXgvZW5lcmd5X21vZGVsLmg+DQorI2luY2x1ZGUgPGxpbnV4L2lu aXQuaD4NCisjaW5jbHVkZSA8bGludXgvaW9wb2xsLmg+DQorI2luY2x1ZGUgPGxpbnV4L2tlcm5l bC5oPg0KKyNpbmNsdWRlIDxsaW51eC9tb2R1bGUuaD4NCisjaW5jbHVkZSA8bGludXgvb2ZfYWRk cmVzcy5oPg0KKyNpbmNsdWRlIDxsaW51eC9vZl9wbGF0Zm9ybS5oPg0KKyNpbmNsdWRlIDxsaW51 eC9wbV9xb3MuaD4NCisjaW5jbHVkZSA8bGludXgvc2xhYi5oPg0KKw0KKyNkZWZpbmUgTFVUX01B WF9FTlRSSUVTCQkJMzJVDQorI2RlZmluZSBMVVRfRlJFUQkJCUdFTk1BU0soMTEsIDApDQorI2Rl ZmluZSBMVVRfUk9XX1NJWkUJCQkweDQNCisjZGVmaW5lIENQVUZSRVFfSFdfU1RBVFVTCQlCSVQo MCkNCisjZGVmaW5lIFNWU19IV19TVEFUVVMJCQlCSVQoMSkNCisjZGVmaW5lIFBPTExfVVNFQwkJ CTEwMDANCisjZGVmaW5lIFRJTUVPVVRfVVNFQwkJCTMwMDAwMA0KKw0KK2VudW0gew0KKwlSRUdf RlJFUV9MVVRfVEFCTEUsDQorCVJFR19GUkVRX0VOQUJMRSwNCisJUkVHX0ZSRVFfUEVSRl9TVEFU RSwNCisJUkVHX0ZSRVFfSFdfU1RBVEUsDQorCVJFR19FTV9QT1dFUl9UQkwsDQorDQorCVJFR19B UlJBWV9TSVpFLA0KK307DQorDQorc3RydWN0IGNwdWZyZXFfbXRrIHsNCisJc3RydWN0IGNwdWZy ZXFfZnJlcXVlbmN5X3RhYmxlICp0YWJsZTsNCisJdm9pZCBfX2lvbWVtICpyZWdfYmFzZXNbUkVH X0FSUkFZX1NJWkVdOw0KKwlpbnQgbnJfb3BwOw0KKwljcHVtYXNrX3QgcmVsYXRlZF9jcHVzOw0K K307DQorDQorc3RhdGljIGNvbnN0IHUxNiBjcHVmcmVxX210a19vZmZzZXRzW1JFR19BUlJBWV9T SVpFXSA9IHsNCisJW1JFR19GUkVRX0xVVF9UQUJMRV0JPSAweDAsDQorCVtSRUdfRlJFUV9FTkFC TEVdCT0gMHg4NCwNCisJW1JFR19GUkVRX1BFUkZfU1RBVEVdCT0gMHg4OCwNCisJW1JFR19GUkVR X0hXX1NUQVRFXQk9IDB4OGMsDQorCVtSRUdfRU1fUE9XRVJfVEJMXQk9IDB4M0QwLA0KK307DQor DQorc3RhdGljIHN0cnVjdCBjcHVmcmVxX210ayAqbXRrX2ZyZXFfZG9tYWluX21hcFtOUl9DUFVT XTsNCisNCitzdGF0aWMgaW50IG10a19jcHVmcmVxX2dldF9jcHVfcG93ZXIodW5zaWduZWQgbG9u ZyAqbVcsDQorCQkJCSAgICAgdW5zaWduZWQgbG9uZyAqS0h6LCBzdHJ1Y3QgZGV2aWNlICpjcHVf ZGV2KQ0KK3sNCisJc3RydWN0IGNwdWZyZXFfbXRrICpjID0gbXRrX2ZyZXFfZG9tYWluX21hcFtj cHVfZGV2LT5pZF07DQorCWludCBpOw0KKw0KKwlmb3IgKGkgPSAwOyBpIDwgYy0+bnJfb3BwOyBp KyspIHsNCisJCWlmIChjLT50YWJsZVtpXS5mcmVxdWVuY3kgPCAqS0h6KQ0KKwkJCWJyZWFrOw0K Kwl9DQorCWktLTsNCisNCisJKktIeiA9IGMtPnRhYmxlW2ldLmZyZXF1ZW5jeTsNCisJKm1XID0g cmVhZGxfcmVsYXhlZChjLT5yZWdfYmFzZXNbUkVHX0VNX1BPV0VSX1RCTF0gKw0KKwkJCSAgICBp ICogTFVUX1JPV19TSVpFKSAvIDEwMDA7DQorDQorCXJldHVybiAwOw0KK30NCisNCitzdGF0aWMg aW50IG10a19jcHVmcmVxX2h3X3RhcmdldF9pbmRleChzdHJ1Y3QgY3B1ZnJlcV9wb2xpY3kgKnBv bGljeSwNCisJCQkJICAgICAgIHVuc2lnbmVkIGludCBpbmRleCkNCit7DQorCXN0cnVjdCBjcHVm cmVxX210ayAqYyA9IHBvbGljeS0+ZHJpdmVyX2RhdGE7DQorDQorCXdyaXRlbF9yZWxheGVkKGlu ZGV4LCBjLT5yZWdfYmFzZXNbUkVHX0ZSRVFfUEVSRl9TVEFURV0pOw0KKw0KKwlyZXR1cm4gMDsN Cit9DQorDQorc3RhdGljIHVuc2lnbmVkIGludCBtdGtfY3B1ZnJlcV9od19nZXQodW5zaWduZWQg aW50IGNwdSkNCit7DQorCXN0cnVjdCBjcHVmcmVxX210ayAqYzsNCisJdW5zaWduZWQgaW50IGlu ZGV4Ow0KKw0KKwljID0gbXRrX2ZyZXFfZG9tYWluX21hcFtjcHVdOw0KKw0KKwlpbmRleCA9IHJl YWRsX3JlbGF4ZWQoYy0+cmVnX2Jhc2VzW1JFR19GUkVRX1BFUkZfU1RBVEVdKTsNCisJaW5kZXgg PSBtaW4oaW5kZXgsIExVVF9NQVhfRU5UUklFUyAtIDEpOw0KKw0KKwlyZXR1cm4gYy0+dGFibGVb aW5kZXhdLmZyZXF1ZW5jeTsNCit9DQorDQorc3RhdGljIGludCBtdGtfY3B1ZnJlcV9od19jcHVf aW5pdChzdHJ1Y3QgY3B1ZnJlcV9wb2xpY3kgKnBvbGljeSkNCit7DQorCXN0cnVjdCBjcHVmcmVx X210ayAqYzsNCisJc3RydWN0IGRldmljZSAqY3B1X2RldjsNCisJc3RydWN0IGVtX2RhdGFfY2Fs bGJhY2sgZW1fY2IgPSBFTV9EQVRBX0NCKG10a19jcHVmcmVxX2dldF9jcHVfcG93ZXIpOw0KKwlz dHJ1Y3QgcG1fcW9zX3JlcXVlc3QgKnFvc19yZXF1ZXN0Ow0KKwlpbnQgc2lnLCBwd3JfaHcgPSBD UFVGUkVRX0hXX1NUQVRVUyB8IFNWU19IV19TVEFUVVM7DQorDQorCXFvc19yZXF1ZXN0ID0ga3ph bGxvYyhzaXplb2YoKnFvc19yZXF1ZXN0KSwgR0ZQX0tFUk5FTCk7DQorCWlmICghcW9zX3JlcXVl c3QpDQorCQlyZXR1cm4gLUVOT01FTTsNCisNCisJY3B1X2RldiA9IGdldF9jcHVfZGV2aWNlKHBv bGljeS0+Y3B1KTsNCisJaWYgKCFjcHVfZGV2KSB7DQorCQlwcl9lcnIoImZhaWxlZCB0byBnZXQg Y3B1JWQgZGV2aWNlXG4iLCBwb2xpY3ktPmNwdSk7DQorCQlyZXR1cm4gLUVOT0RFVjsNCisJfQ0K Kw0KKwljID0gbXRrX2ZyZXFfZG9tYWluX21hcFtwb2xpY3ktPmNwdV07DQorCWlmICghYykgew0K KwkJcHJfZXJyKCJObyBzY2FsaW5nIHN1cHBvcnQgZm9yIENQVSVkXG4iLCBwb2xpY3ktPmNwdSk7 DQorCQlyZXR1cm4gLUVOT0RFVjsNCisJfQ0KKw0KKwljcHVtYXNrX2NvcHkocG9saWN5LT5jcHVz LCAmYy0+cmVsYXRlZF9jcHVzKTsNCisNCisJcG9saWN5LT5mcmVxX3RhYmxlID0gYy0+dGFibGU7 DQorCXBvbGljeS0+ZHJpdmVyX2RhdGEgPSBjOw0KKw0KKwkvKiBMZXQgQ1BVcyBsZWF2ZSBpZGxl LW9mZiBzdGF0ZSBmb3IgU1ZTIENQVSBpbml0aWFsaXppbmcgKi8NCisJY3B1X2xhdGVuY3lfcW9z X2FkZF9yZXF1ZXN0KHFvc19yZXF1ZXN0LCAwKTsNCisNCisJLyogSFcgc2hvdWxkIGJlIGluIGVu YWJsZWQgc3RhdGUgdG8gcHJvY2VlZCBub3cgKi8NCisJd3JpdGVsX3JlbGF4ZWQoMHgxLCBjLT5y ZWdfYmFzZXNbUkVHX0ZSRVFfRU5BQkxFXSk7DQorDQorCWlmIChyZWFkbF9wb2xsX3RpbWVvdXQo Yy0+cmVnX2Jhc2VzW1JFR19GUkVRX0hXX1NUQVRFXSwgc2lnLA0KKwkJCSAgICAgICAoc2lnICYg cHdyX2h3KSA9PSBwd3JfaHcsIFBPTExfVVNFQywNCisJCQkgICAgICAgVElNRU9VVF9VU0VDKSkg ew0KKwkJaWYgKCEoc2lnICYgQ1BVRlJFUV9IV19TVEFUVVMpKSB7DQorCQkJcHJfaW5mbygiY3B1 ZnJlcSBoYXJkd2FyZSBvZiBDUFUlZCBpcyBub3QgZW5hYmxlZFxuIiwNCisJCQkJcG9saWN5LT5j cHUpOw0KKwkJCXJldHVybiAtRU5PREVWOw0KKwkJfQ0KKw0KKwkJcHJfaW5mbygiU1ZTIG9mIENQ VSVkIGlzIG5vdCBlbmFibGVkXG4iLCBwb2xpY3ktPmNwdSk7DQorCX0NCisNCisJZW1fZGV2X3Jl Z2lzdGVyX3BlcmZfZG9tYWluKGNwdV9kZXYsIGMtPm5yX29wcCwgJmVtX2NiLCBwb2xpY3ktPmNw dXMpOw0KKw0KKwljcHVfbGF0ZW5jeV9xb3NfcmVtb3ZlX3JlcXVlc3QocW9zX3JlcXVlc3QpOw0K KwlrZnJlZShxb3NfcmVxdWVzdCk7DQorDQorCXJldHVybiAwOw0KK30NCisNCitzdGF0aWMgaW50 IG10a19jcHVmcmVxX2h3X2NwdV9leGl0KHN0cnVjdCBjcHVmcmVxX3BvbGljeSAqcG9saWN5KQ0K K3sNCisJc3RydWN0IGNwdWZyZXFfbXRrICpjOw0KKw0KKwljID0gbXRrX2ZyZXFfZG9tYWluX21h cFtwb2xpY3ktPmNwdV07DQorCWlmICghYykgew0KKwkJcHJfZXJyKCJObyBzY2FsaW5nIHN1cHBv cnQgZm9yIENQVSVkXG4iLCBwb2xpY3ktPmNwdSk7DQorCQlyZXR1cm4gLUVOT0RFVjsNCisJfQ0K Kw0KKwkvKiBIVyBzaG91bGQgYmUgaW4gcGF1c2VkIHN0YXRlIG5vdyAqLw0KKwl3cml0ZWxfcmVs YXhlZCgweDAsIGMtPnJlZ19iYXNlc1tSRUdfRlJFUV9FTkFCTEVdKTsNCisNCisJcmV0dXJuIDA7 DQorfQ0KKw0KK3N0YXRpYyBzdHJ1Y3QgY3B1ZnJlcV9kcml2ZXIgY3B1ZnJlcV9tdGtfaHdfZHJp dmVyID0gew0KKwkuZmxhZ3MJCT0gQ1BVRlJFUV9TVElDS1kgfCBDUFVGUkVRX05FRURfSU5JVElB TF9GUkVRX0NIRUNLIHwNCisJCQkgIENQVUZSRVFfSEFWRV9HT1ZFUk5PUl9QRVJfUE9MSUNZIHwN CisJCQkgIENQVUZSRVFfSVNfQ09PTElOR19ERVYsDQorCS52ZXJpZnkJCT0gY3B1ZnJlcV9nZW5l cmljX2ZyZXF1ZW5jeV90YWJsZV92ZXJpZnksDQorCS50YXJnZXRfaW5kZXgJPSBtdGtfY3B1ZnJl cV9od190YXJnZXRfaW5kZXgsDQorCS5nZXQJCT0gbXRrX2NwdWZyZXFfaHdfZ2V0LA0KKwkuaW5p dAkJPSBtdGtfY3B1ZnJlcV9od19jcHVfaW5pdCwNCisJLmV4aXQJCT0gbXRrX2NwdWZyZXFfaHdf Y3B1X2V4aXQsDQorCS5uYW1lCQk9ICJtdGstY3B1ZnJlcS1odyIsDQorCS5hdHRyCQk9IGNwdWZy ZXFfZ2VuZXJpY19hdHRyLA0KK307DQorDQorc3RhdGljIGludCBtdGtfY3B1X2NyZWF0ZV9mcmVx X3RhYmxlKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2UgKnBkZXYsDQorCQkJCSAgICAgc3RydWN0IGNw dWZyZXFfbXRrICpjKQ0KK3sNCisJc3RydWN0IGRldmljZSAqZGV2ID0gJnBkZXYtPmRldjsNCisJ dm9pZCBfX2lvbWVtICpiYXNlX3RhYmxlOw0KKwl1MzIgZGF0YSwgaSwgZnJlcSwgcHJldl9mcmVx ID0gMDsNCisNCisJYy0+dGFibGUgPSBkZXZtX2tjYWxsb2MoZGV2LCBMVVRfTUFYX0VOVFJJRVMg KyAxLA0KKwkJCQlzaXplb2YoKmMtPnRhYmxlKSwgR0ZQX0tFUk5FTCk7DQorCWlmICghYy0+dGFi bGUpDQorCQlyZXR1cm4gLUVOT01FTTsNCisNCisJYmFzZV90YWJsZSA9IGMtPnJlZ19iYXNlc1tS RUdfRlJFUV9MVVRfVEFCTEVdOw0KKw0KKwlmb3IgKGkgPSAwOyBpIDwgTFVUX01BWF9FTlRSSUVT OyBpKyspIHsNCisJCWRhdGEgPSByZWFkbF9yZWxheGVkKGJhc2VfdGFibGUgKyAoaSAqIExVVF9S T1dfU0laRSkpOw0KKwkJZnJlcSA9IEZJRUxEX0dFVChMVVRfRlJFUSwgZGF0YSkgKiAxMDAwOw0K Kw0KKwkJaWYgKGZyZXEgPT0gcHJldl9mcmVxKQ0KKwkJCWJyZWFrOw0KKw0KKwkJYy0+dGFibGVb aV0uZnJlcXVlbmN5ID0gZnJlcTsNCisNCisJCWRldl9kYmcoZGV2LCAiaW5kZXg9JWQgZnJlcT0l ZFxuIiwNCisJCQlpLCBjLT50YWJsZVtpXS5mcmVxdWVuY3kpOw0KKw0KKwkJcHJldl9mcmVxID0g ZnJlcTsNCisJfQ0KKw0KKwljLT50YWJsZVtpXS5mcmVxdWVuY3kgPSBDUFVGUkVRX1RBQkxFX0VO RDsNCisJYy0+bnJfb3BwID0gaTsNCisNCisJcmV0dXJuIDA7DQorfQ0KKw0KK3N0YXRpYyBpbnQg bXRrX2dldF9yZWxhdGVkX2NwdXMoaW50IGluZGV4LCBzdHJ1Y3QgY3B1ZnJlcV9tdGsgKmMpDQor ew0KKwlzdHJ1Y3QgZGV2aWNlX25vZGUgKmNwdV9ucDsNCisJc3RydWN0IG9mX3BoYW5kbGVfYXJn cyBhcmdzOw0KKwlpbnQgY3B1LCByZXQ7DQorDQorCWZvcl9lYWNoX3Bvc3NpYmxlX2NwdShjcHUp IHsNCisJCWNwdV9ucCA9IG9mX2NwdV9kZXZpY2Vfbm9kZV9nZXQoY3B1KTsNCisJCWlmICghY3B1 X25wKQ0KKwkJCWNvbnRpbnVlOw0KKw0KKwkJcmV0ID0gb2ZfcGFyc2VfcGhhbmRsZV93aXRoX2Fy Z3MoY3B1X25wLCAibWVkaWF0ZWssZnJlcS1kb21haW4iLA0KKwkJCQkJCSAiI2ZyZXEtZG9tYWlu LWNlbGxzIiwgMCwNCisJCQkJCQkgJmFyZ3MpOw0KKwkJb2Zfbm9kZV9wdXQoY3B1X25wKTsNCisJ CWlmIChyZXQgPCAwKQ0KKwkJCWNvbnRpbnVlOw0KKw0KKwkJaWYgKGluZGV4ID09IGFyZ3MuYXJn c1swXSkgew0KKwkJCWNwdW1hc2tfc2V0X2NwdShjcHUsICZjLT5yZWxhdGVkX2NwdXMpOw0KKwkJ CW10a19mcmVxX2RvbWFpbl9tYXBbY3B1XSA9IGM7DQorCQl9DQorCX0NCisNCisJcmV0dXJuIDA7 DQorfQ0KKw0KK3N0YXRpYyBpbnQgbXRrX2NwdV9yZXNvdXJjZXNfaW5pdChzdHJ1Y3QgcGxhdGZv cm1fZGV2aWNlICpwZGV2LA0KKwkJCQkgIHVuc2lnbmVkIGludCBjcHUsIGludCBpbmRleCwNCisJ CQkJICBjb25zdCB1MTYgKm9mZnNldHMpDQorew0KKwlzdHJ1Y3QgY3B1ZnJlcV9tdGsgKmM7DQor CXN0cnVjdCBkZXZpY2UgKmRldiA9ICZwZGV2LT5kZXY7DQorCWludCByZXQsIGk7DQorCXZvaWQg X19pb21lbSAqYmFzZTsNCisNCisJaWYgKG10a19mcmVxX2RvbWFpbl9tYXBbY3B1XSkNCisJCXJl dHVybiAwOw0KKw0KKwljID0gZGV2bV9remFsbG9jKGRldiwgc2l6ZW9mKCpjKSwgR0ZQX0tFUk5F TCk7DQorCWlmICghYykNCisJCXJldHVybiAtRU5PTUVNOw0KKw0KKwliYXNlID0gZGV2bV9wbGF0 Zm9ybV9pb3JlbWFwX3Jlc291cmNlKHBkZXYsIGluZGV4KTsNCisJaWYgKElTX0VSUihiYXNlKSkN CisJCXJldHVybiBQVFJfRVJSKGJhc2UpOw0KKw0KKwlmb3IgKGkgPSBSRUdfRlJFUV9MVVRfVEFC TEU7IGkgPCBSRUdfQVJSQVlfU0laRTsgaSsrKQ0KKwkJYy0+cmVnX2Jhc2VzW2ldID0gYmFzZSAr IG9mZnNldHNbaV07DQorDQorCXJldCA9IG10a19nZXRfcmVsYXRlZF9jcHVzKGluZGV4LCBjKTsN CisJaWYgKHJldCkgew0KKwkJZGV2X2VycihkZXYsICJEb21haW4tJWQgZmFpbGVkIHRvIGdldCBy ZWxhdGVkIENQVXNcbiIsIGluZGV4KTsNCisJCXJldHVybiByZXQ7DQorCX0NCisNCisJcmV0ID0g bXRrX2NwdV9jcmVhdGVfZnJlcV90YWJsZShwZGV2LCBjKTsNCisJaWYgKHJldCkgew0KKwkJZGV2 X2VycihkZXYsICJEb21haW4tJWQgZmFpbGVkIHRvIGNyZWF0ZSBmcmVxIHRhYmxlXG4iLCBpbmRl eCk7DQorCQlyZXR1cm4gcmV0Ow0KKwl9DQorDQorCXJldHVybiAwOw0KK30NCisNCitzdGF0aWMg aW50IG10a19jcHVmcmVxX2h3X2RyaXZlcl9wcm9iZShzdHJ1Y3QgcGxhdGZvcm1fZGV2aWNlICpw ZGV2KQ0KK3sNCisJc3RydWN0IGRldmljZV9ub2RlICpjcHVfbnA7DQorCXN0cnVjdCBvZl9waGFu ZGxlX2FyZ3MgYXJnczsNCisJY29uc3QgdTE2ICpvZmZzZXRzOw0KKwl1bnNpZ25lZCBpbnQgY3B1 Ow0KKwlpbnQgcmV0Ow0KKw0KKwlvZmZzZXRzID0gb2ZfZGV2aWNlX2dldF9tYXRjaF9kYXRhKCZw ZGV2LT5kZXYpOw0KKwlpZiAoIW9mZnNldHMpDQorCQlyZXR1cm4gLUVJTlZBTDsNCisNCisJZm9y X2VhY2hfcG9zc2libGVfY3B1KGNwdSkgew0KKwkJY3B1X25wID0gb2ZfY3B1X2RldmljZV9ub2Rl X2dldChjcHUpOw0KKwkJaWYgKCFjcHVfbnApIHsNCisJCQlkZXZfZXJyKCZwZGV2LT5kZXYsICJG YWlsZWQgdG8gZ2V0IGNwdSAlZCBkZXZpY2VcbiIsDQorCQkJCWNwdSk7DQorCQkJcmV0dXJuIC1F Tk9ERVY7DQorCQl9DQorDQorCQlyZXQgPSBvZl9wYXJzZV9waGFuZGxlX3dpdGhfYXJncyhjcHVf bnAsICJtZWRpYXRlayxmcmVxLWRvbWFpbiIsDQorCQkJCQkJICIjZnJlcS1kb21haW4tY2VsbHMi LCAwLA0KKwkJCQkJCSAmYXJncyk7DQorCQlpZiAocmV0IDwgMCkNCisJCQlyZXR1cm4gcmV0Ow0K Kw0KKwkJLyogR2V0IHRoZSBiYXNlcyBvZiBjcHVmcmVxIGZvciBkb21haW5zICovDQorCQlyZXQg PSBtdGtfY3B1X3Jlc291cmNlc19pbml0KHBkZXYsIGNwdSwgYXJncy5hcmdzWzBdLCBvZmZzZXRz KTsNCisJCWlmIChyZXQpIHsNCisJCQlkZXZfZXJyKCZwZGV2LT5kZXYsICJDUFVGcmVxIHJlc291 cmNlIGluaXQgZmFpbGVkXG4iKTsNCisJCQlyZXR1cm4gcmV0Ow0KKwkJfQ0KKwl9DQorDQorCXJl dCA9IGNwdWZyZXFfcmVnaXN0ZXJfZHJpdmVyKCZjcHVmcmVxX210a19od19kcml2ZXIpOw0KKwlp ZiAocmV0KSB7DQorCQlkZXZfZXJyKCZwZGV2LT5kZXYsICJDUFVGcmVxIEhXIGRyaXZlciBmYWls ZWQgdG8gcmVnaXN0ZXJcbiIpOw0KKwkJcmV0dXJuIHJldDsNCisJfQ0KKw0KKwlyZXR1cm4gMDsN Cit9DQorDQorc3RhdGljIGludCBtdGtfY3B1ZnJlcV9od19kcml2ZXJfcmVtb3ZlKHN0cnVjdCBw bGF0Zm9ybV9kZXZpY2UgKnBkZXYpDQorew0KKwlyZXR1cm4gY3B1ZnJlcV91bnJlZ2lzdGVyX2Ry aXZlcigmY3B1ZnJlcV9tdGtfaHdfZHJpdmVyKTsNCit9DQorDQorc3RhdGljIGNvbnN0IHN0cnVj dCBvZl9kZXZpY2VfaWQgbXRrX2NwdWZyZXFfaHdfbWF0Y2hbXSA9IHsNCisJeyAuY29tcGF0aWJs ZSA9ICJtZWRpYXRlayxjcHVmcmVxLWh3IiwgLmRhdGEgPSAmY3B1ZnJlcV9tdGtfb2Zmc2V0cyB9 LA0KKwl7fQ0KK307DQorDQorc3RhdGljIHN0cnVjdCBwbGF0Zm9ybV9kcml2ZXIgbXRrX2NwdWZy ZXFfaHdfZHJpdmVyID0gew0KKwkucHJvYmUgPSBtdGtfY3B1ZnJlcV9od19kcml2ZXJfcHJvYmUs DQorCS5yZW1vdmUgPSBtdGtfY3B1ZnJlcV9od19kcml2ZXJfcmVtb3ZlLA0KKwkuZHJpdmVyID0g ew0KKwkJLm5hbWUgPSAibXRrLWNwdWZyZXEtaHciLA0KKwkJLm9mX21hdGNoX3RhYmxlID0gbXRr X2NwdWZyZXFfaHdfbWF0Y2gsDQorCX0sDQorfTsNCittb2R1bGVfcGxhdGZvcm1fZHJpdmVyKG10 a19jcHVmcmVxX2h3X2RyaXZlcik7DQorDQorTU9EVUxFX0RFU0NSSVBUSU9OKCJNZWRpYXRlayBj cHVmcmVxLWh3IGRyaXZlciIpOw0KK01PRFVMRV9MSUNFTlNFKCJHUEwgdjIiKTsNCi0tIA0KMS43 LjkuNQ0K From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-12.8 required=3.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH, MAILING_LIST_MULTI,SIGNED_OFF_BY,SPF_HELO_NONE,SPF_PASS,UNPARSEABLE_RELAY, URIBL_BLOCKED,USER_AGENT_GIT autolearn=ham autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 898ACC388F9 for ; Mon, 26 Oct 2020 08:19:49 +0000 (UTC) Received: from merlin.infradead.org (merlin.infradead.org [205.233.59.134]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id 0D20720878 for ; Mon, 26 Oct 2020 08:19:49 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=lists.infradead.org header.i=@lists.infradead.org header.b="EyvYKr1K"; dkim=fail reason="signature verification failed" (1024-bit key) header.d=mediatek.com header.i=@mediatek.com header.b="jm00NxZS" DMARC-Filter: OpenDMARC Filter v1.3.2 mail.kernel.org 0D20720878 Authentication-Results: mail.kernel.org; dmarc=fail (p=none dis=none) header.from=mediatek.com Authentication-Results: mail.kernel.org; spf=none smtp.mailfrom=linux-mediatek-bounces+linux-mediatek=archiver.kernel.org@lists.infradead.org DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=merlin.20170209; h=Sender:Content-Transfer-Encoding: Content-Type:Cc:List-Subscribe:List-Help:List-Post:List-Archive: List-Unsubscribe:List-Id:MIME-Version:References:In-Reply-To:Message-ID:Date: Subject:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=l1DP5UNyQS8LENHanMlcb2JWXFLXk9BJj9qH8DScRjo=; b=EyvYKr1KSg4ZT5SSgNT+oyWjS LFEAdhwKeTO4xjlk/xwjse7d2UKNAhRQ7MFG0TDnG9EBTxcVuuFXao8TuLqUzsBaFoj4wYOqGorDW FitPqTiSjOjTMwMxj+4za0C5eM4bExkHhKePNSOx2jNTKXjzW7BJKW+xTvKrNqTNC1TfxvqFZAjEn PCxi1tZrdIBD++1vsB81A50kVoReOybBVk1w6c4BNZzh809UpPcsU3797kTsUZcm7pVVJERfZAMca 4T1wh/EJzUeesDUNWyJQ2/9ayX/9R/+mon1DT5DGryMX5bGxd8tlMVtpG3h3skPziCjjawKHJpAUi RRDtv6e5w==; Received: from localhost ([::1] helo=merlin.infradead.org) by merlin.infradead.org with esmtp (Exim 4.92.3 #3 (Red Hat Linux)) id 1kWxj7-0006mi-FD; Mon, 26 Oct 2020 08:19:37 +0000 Received: from mailgw02.mediatek.com ([216.200.240.185]) by merlin.infradead.org with esmtps (Exim 4.92.3 #3 (Red Hat Linux)) id 1kWxit-0006gi-W9; Mon, 26 Oct 2020 08:19:25 +0000 X-UUID: 3201fda57fe846d2aa5cbf0c8f9ac692-20201026 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=mediatek.com; s=dk; h=Content-Transfer-Encoding:Content-Type:MIME-Version:References:In-Reply-To:Message-ID:Date:Subject:CC:To:From; bh=s89f08KvBYl1d0htgXzsoi2iHSJgKoDYNXWWA86n02U=; b=jm00NxZS9vVSeZArMqOgaEXsPcCPAe6Rv14yWJf/tCDCOoP2WaXbHg38B7EjRt29XxX+UqRWHyGP75Iiev8PQumVDe7CcLqBpliN7NeTaSM3L4VbldKAUQqe7ZMglKyyKBJWJg9j0IvZqvxmFSuWYRDgWyhF56YY8/NHqd4ATEI=; X-UUID: 3201fda57fe846d2aa5cbf0c8f9ac692-20201026 Received: from mtkcas66.mediatek.inc [(172.29.193.44)] by mailgw02.mediatek.com (envelope-from ) (musrelay.mediatek.com ESMTP with TLSv1.2 ECDHE-RSA-AES256-SHA384 256/256) with ESMTP id 1733819593; Mon, 26 Oct 2020 00:19:17 -0800 Received: from MTKMBS07N2.mediatek.inc (172.21.101.141) by MTKMBS62DR.mediatek.inc (172.29.94.18) with Microsoft SMTP Server (TLS) id 15.0.1497.2; Mon, 26 Oct 2020 01:19:16 -0700 Received: from mtkcas08.mediatek.inc (172.21.101.126) by mtkmbs07n2.mediatek.inc (172.21.101.141) with Microsoft SMTP Server (TLS) id 15.0.1497.2; Mon, 26 Oct 2020 16:19:14 +0800 Received: from mtkswgap22.mediatek.inc (172.21.77.33) by mtkcas08.mediatek.inc (172.21.101.73) with Microsoft SMTP Server id 15.0.1497.2 via Frontend Transport; Mon, 26 Oct 2020 16:19:13 +0800 From: Hector Yuan To: , , , "Rob Herring" , Sudeep Holla , "Rafael J. Wysocki" , Viresh Kumar , "Maxime Ripard" , Santosh Shilimkar , "Amit Kucheria" , Stephen Boyd , "Ulf Hansson" , Dave Gerlach , "Florian Fainelli" , Robin Murphy , "Lorenzo Pieralisi" , Subject: [PATCH v8 1/3] cpufreq: mediatek-hw: Add support for CPUFREQ HW Date: Mon, 26 Oct 2020 16:19:07 +0800 Message-ID: <1603700349-5922-2-git-send-email-hector.yuan@mediatek.com> X-Mailer: git-send-email 1.7.9.5 In-Reply-To: <1603700349-5922-1-git-send-email-hector.yuan@mediatek.com> References: <1603700349-5922-1-git-send-email-hector.yuan@mediatek.com> MIME-Version: 1.0 X-MTK: N X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20201026_041924_322375_6D03009C X-CRM114-Status: GOOD ( 27.88 ) X-BeenThere: linux-mediatek@lists.infradead.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: hector.yuan@mediatek.com, linux-kernel@vger.kernel.org, wsd_upstream@mediatek.com Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Sender: "Linux-mediatek" Errors-To: linux-mediatek-bounces+linux-mediatek=archiver.kernel.org@lists.infradead.org From: "Hector.Yuan" Add cpufreq HW support. Signed-off-by: Hector.Yuan --- drivers/cpufreq/Kconfig.arm | 12 ++ drivers/cpufreq/Makefile | 1 + drivers/cpufreq/mediatek-cpufreq-hw.c | 343 +++++++++++++++++++++++++++++++++ 3 files changed, 356 insertions(+) create mode 100644 drivers/cpufreq/mediatek-cpufreq-hw.c diff --git a/drivers/cpufreq/Kconfig.arm b/drivers/cpufreq/Kconfig.arm index cb72fb5..b9d17c5 100644 --- a/drivers/cpufreq/Kconfig.arm +++ b/drivers/cpufreq/Kconfig.arm @@ -123,6 +123,18 @@ config ARM_MEDIATEK_CPUFREQ help This adds the CPUFreq driver support for MediaTek SoCs. +config ARM_MEDIATEK_CPUFREQ_HW + tristate "MediaTek CPUFreq HW driver" + depends on ARCH_MEDIATEK || COMPILE_TEST + default m + help + Support for the CPUFreq HW driver. + Some MediaTek chipsets have a HW engine to offload the steps + necessary for changing the frequency of the CPUs. Firmware loaded + in this engine exposes a programming interface to the OS. + The driver implements the cpufreq interface for this HW engine. + Say Y if you want to support CPUFreq HW. + config ARM_OMAP2PLUS_CPUFREQ bool "TI OMAP2+" depends on ARCH_OMAP2PLUS diff --git a/drivers/cpufreq/Makefile b/drivers/cpufreq/Makefile index f1b7e3d..ffc61cd 100644 --- a/drivers/cpufreq/Makefile +++ b/drivers/cpufreq/Makefile @@ -57,6 +57,7 @@ obj-$(CONFIG_ARM_IMX6Q_CPUFREQ) += imx6q-cpufreq.o obj-$(CONFIG_ARM_IMX_CPUFREQ_DT) += imx-cpufreq-dt.o obj-$(CONFIG_ARM_KIRKWOOD_CPUFREQ) += kirkwood-cpufreq.o obj-$(CONFIG_ARM_MEDIATEK_CPUFREQ) += mediatek-cpufreq.o +obj-$(CONFIG_ARM_MEDIATEK_CPUFREQ_HW) += mediatek-cpufreq-hw.o obj-$(CONFIG_MACH_MVEBU_V7) += mvebu-cpufreq.o obj-$(CONFIG_ARM_OMAP2PLUS_CPUFREQ) += omap-cpufreq.o obj-$(CONFIG_ARM_PXA2xx_CPUFREQ) += pxa2xx-cpufreq.o diff --git a/drivers/cpufreq/mediatek-cpufreq-hw.c b/drivers/cpufreq/mediatek-cpufreq-hw.c new file mode 100644 index 0000000..3af36b0 --- /dev/null +++ b/drivers/cpufreq/mediatek-cpufreq-hw.c @@ -0,0 +1,343 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (c) 2020 MediaTek Inc. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define LUT_MAX_ENTRIES 32U +#define LUT_FREQ GENMASK(11, 0) +#define LUT_ROW_SIZE 0x4 +#define CPUFREQ_HW_STATUS BIT(0) +#define SVS_HW_STATUS BIT(1) +#define POLL_USEC 1000 +#define TIMEOUT_USEC 300000 + +enum { + REG_FREQ_LUT_TABLE, + REG_FREQ_ENABLE, + REG_FREQ_PERF_STATE, + REG_FREQ_HW_STATE, + REG_EM_POWER_TBL, + + REG_ARRAY_SIZE, +}; + +struct cpufreq_mtk { + struct cpufreq_frequency_table *table; + void __iomem *reg_bases[REG_ARRAY_SIZE]; + int nr_opp; + cpumask_t related_cpus; +}; + +static const u16 cpufreq_mtk_offsets[REG_ARRAY_SIZE] = { + [REG_FREQ_LUT_TABLE] = 0x0, + [REG_FREQ_ENABLE] = 0x84, + [REG_FREQ_PERF_STATE] = 0x88, + [REG_FREQ_HW_STATE] = 0x8c, + [REG_EM_POWER_TBL] = 0x3D0, +}; + +static struct cpufreq_mtk *mtk_freq_domain_map[NR_CPUS]; + +static int mtk_cpufreq_get_cpu_power(unsigned long *mW, + unsigned long *KHz, struct device *cpu_dev) +{ + struct cpufreq_mtk *c = mtk_freq_domain_map[cpu_dev->id]; + int i; + + for (i = 0; i < c->nr_opp; i++) { + if (c->table[i].frequency < *KHz) + break; + } + i--; + + *KHz = c->table[i].frequency; + *mW = readl_relaxed(c->reg_bases[REG_EM_POWER_TBL] + + i * LUT_ROW_SIZE) / 1000; + + return 0; +} + +static int mtk_cpufreq_hw_target_index(struct cpufreq_policy *policy, + unsigned int index) +{ + struct cpufreq_mtk *c = policy->driver_data; + + writel_relaxed(index, c->reg_bases[REG_FREQ_PERF_STATE]); + + return 0; +} + +static unsigned int mtk_cpufreq_hw_get(unsigned int cpu) +{ + struct cpufreq_mtk *c; + unsigned int index; + + c = mtk_freq_domain_map[cpu]; + + index = readl_relaxed(c->reg_bases[REG_FREQ_PERF_STATE]); + index = min(index, LUT_MAX_ENTRIES - 1); + + return c->table[index].frequency; +} + +static int mtk_cpufreq_hw_cpu_init(struct cpufreq_policy *policy) +{ + struct cpufreq_mtk *c; + struct device *cpu_dev; + struct em_data_callback em_cb = EM_DATA_CB(mtk_cpufreq_get_cpu_power); + struct pm_qos_request *qos_request; + int sig, pwr_hw = CPUFREQ_HW_STATUS | SVS_HW_STATUS; + + qos_request = kzalloc(sizeof(*qos_request), GFP_KERNEL); + if (!qos_request) + return -ENOMEM; + + cpu_dev = get_cpu_device(policy->cpu); + if (!cpu_dev) { + pr_err("failed to get cpu%d device\n", policy->cpu); + return -ENODEV; + } + + c = mtk_freq_domain_map[policy->cpu]; + if (!c) { + pr_err("No scaling support for CPU%d\n", policy->cpu); + return -ENODEV; + } + + cpumask_copy(policy->cpus, &c->related_cpus); + + policy->freq_table = c->table; + policy->driver_data = c; + + /* Let CPUs leave idle-off state for SVS CPU initializing */ + cpu_latency_qos_add_request(qos_request, 0); + + /* HW should be in enabled state to proceed now */ + writel_relaxed(0x1, c->reg_bases[REG_FREQ_ENABLE]); + + if (readl_poll_timeout(c->reg_bases[REG_FREQ_HW_STATE], sig, + (sig & pwr_hw) == pwr_hw, POLL_USEC, + TIMEOUT_USEC)) { + if (!(sig & CPUFREQ_HW_STATUS)) { + pr_info("cpufreq hardware of CPU%d is not enabled\n", + policy->cpu); + return -ENODEV; + } + + pr_info("SVS of CPU%d is not enabled\n", policy->cpu); + } + + em_dev_register_perf_domain(cpu_dev, c->nr_opp, &em_cb, policy->cpus); + + cpu_latency_qos_remove_request(qos_request); + kfree(qos_request); + + return 0; +} + +static int mtk_cpufreq_hw_cpu_exit(struct cpufreq_policy *policy) +{ + struct cpufreq_mtk *c; + + c = mtk_freq_domain_map[policy->cpu]; + if (!c) { + pr_err("No scaling support for CPU%d\n", policy->cpu); + return -ENODEV; + } + + /* HW should be in paused state now */ + writel_relaxed(0x0, c->reg_bases[REG_FREQ_ENABLE]); + + return 0; +} + +static struct cpufreq_driver cpufreq_mtk_hw_driver = { + .flags = CPUFREQ_STICKY | CPUFREQ_NEED_INITIAL_FREQ_CHECK | + CPUFREQ_HAVE_GOVERNOR_PER_POLICY | + CPUFREQ_IS_COOLING_DEV, + .verify = cpufreq_generic_frequency_table_verify, + .target_index = mtk_cpufreq_hw_target_index, + .get = mtk_cpufreq_hw_get, + .init = mtk_cpufreq_hw_cpu_init, + .exit = mtk_cpufreq_hw_cpu_exit, + .name = "mtk-cpufreq-hw", + .attr = cpufreq_generic_attr, +}; + +static int mtk_cpu_create_freq_table(struct platform_device *pdev, + struct cpufreq_mtk *c) +{ + struct device *dev = &pdev->dev; + void __iomem *base_table; + u32 data, i, freq, prev_freq = 0; + + c->table = devm_kcalloc(dev, LUT_MAX_ENTRIES + 1, + sizeof(*c->table), GFP_KERNEL); + if (!c->table) + return -ENOMEM; + + base_table = c->reg_bases[REG_FREQ_LUT_TABLE]; + + for (i = 0; i < LUT_MAX_ENTRIES; i++) { + data = readl_relaxed(base_table + (i * LUT_ROW_SIZE)); + freq = FIELD_GET(LUT_FREQ, data) * 1000; + + if (freq == prev_freq) + break; + + c->table[i].frequency = freq; + + dev_dbg(dev, "index=%d freq=%d\n", + i, c->table[i].frequency); + + prev_freq = freq; + } + + c->table[i].frequency = CPUFREQ_TABLE_END; + c->nr_opp = i; + + return 0; +} + +static int mtk_get_related_cpus(int index, struct cpufreq_mtk *c) +{ + struct device_node *cpu_np; + struct of_phandle_args args; + int cpu, ret; + + for_each_possible_cpu(cpu) { + cpu_np = of_cpu_device_node_get(cpu); + if (!cpu_np) + continue; + + ret = of_parse_phandle_with_args(cpu_np, "mediatek,freq-domain", + "#freq-domain-cells", 0, + &args); + of_node_put(cpu_np); + if (ret < 0) + continue; + + if (index == args.args[0]) { + cpumask_set_cpu(cpu, &c->related_cpus); + mtk_freq_domain_map[cpu] = c; + } + } + + return 0; +} + +static int mtk_cpu_resources_init(struct platform_device *pdev, + unsigned int cpu, int index, + const u16 *offsets) +{ + struct cpufreq_mtk *c; + struct device *dev = &pdev->dev; + int ret, i; + void __iomem *base; + + if (mtk_freq_domain_map[cpu]) + return 0; + + c = devm_kzalloc(dev, sizeof(*c), GFP_KERNEL); + if (!c) + return -ENOMEM; + + base = devm_platform_ioremap_resource(pdev, index); + if (IS_ERR(base)) + return PTR_ERR(base); + + for (i = REG_FREQ_LUT_TABLE; i < REG_ARRAY_SIZE; i++) + c->reg_bases[i] = base + offsets[i]; + + ret = mtk_get_related_cpus(index, c); + if (ret) { + dev_err(dev, "Domain-%d failed to get related CPUs\n", index); + return ret; + } + + ret = mtk_cpu_create_freq_table(pdev, c); + if (ret) { + dev_err(dev, "Domain-%d failed to create freq table\n", index); + return ret; + } + + return 0; +} + +static int mtk_cpufreq_hw_driver_probe(struct platform_device *pdev) +{ + struct device_node *cpu_np; + struct of_phandle_args args; + const u16 *offsets; + unsigned int cpu; + int ret; + + offsets = of_device_get_match_data(&pdev->dev); + if (!offsets) + return -EINVAL; + + for_each_possible_cpu(cpu) { + cpu_np = of_cpu_device_node_get(cpu); + if (!cpu_np) { + dev_err(&pdev->dev, "Failed to get cpu %d device\n", + cpu); + return -ENODEV; + } + + ret = of_parse_phandle_with_args(cpu_np, "mediatek,freq-domain", + "#freq-domain-cells", 0, + &args); + if (ret < 0) + return ret; + + /* Get the bases of cpufreq for domains */ + ret = mtk_cpu_resources_init(pdev, cpu, args.args[0], offsets); + if (ret) { + dev_err(&pdev->dev, "CPUFreq resource init failed\n"); + return ret; + } + } + + ret = cpufreq_register_driver(&cpufreq_mtk_hw_driver); + if (ret) { + dev_err(&pdev->dev, "CPUFreq HW driver failed to register\n"); + return ret; + } + + return 0; +} + +static int mtk_cpufreq_hw_driver_remove(struct platform_device *pdev) +{ + return cpufreq_unregister_driver(&cpufreq_mtk_hw_driver); +} + +static const struct of_device_id mtk_cpufreq_hw_match[] = { + { .compatible = "mediatek,cpufreq-hw", .data = &cpufreq_mtk_offsets }, + {} +}; + +static struct platform_driver mtk_cpufreq_hw_driver = { + .probe = mtk_cpufreq_hw_driver_probe, + .remove = mtk_cpufreq_hw_driver_remove, + .driver = { + .name = "mtk-cpufreq-hw", + .of_match_table = mtk_cpufreq_hw_match, + }, +}; +module_platform_driver(mtk_cpufreq_hw_driver); + +MODULE_DESCRIPTION("Mediatek cpufreq-hw driver"); +MODULE_LICENSE("GPL v2"); -- 1.7.9.5 _______________________________________________ Linux-mediatek mailing list Linux-mediatek@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-mediatek From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-12.8 required=3.0 tests=BAYES_00,DKIMWL_WL_HIGH, DKIM_SIGNED,DKIM_VALID,HEADER_FROM_DIFFERENT_DOMAINS,INCLUDES_PATCH, MAILING_LIST_MULTI,SIGNED_OFF_BY,SPF_HELO_NONE,SPF_PASS,UNPARSEABLE_RELAY, URIBL_BLOCKED,USER_AGENT_GIT autolearn=unavailable autolearn_force=no version=3.4.0 Received: from mail.kernel.org (mail.kernel.org [198.145.29.99]) by smtp.lore.kernel.org (Postfix) with ESMTP id 88DD7C2D0A3 for ; Mon, 26 Oct 2020 08:21:11 +0000 (UTC) Received: from merlin.infradead.org (merlin.infradead.org [205.233.59.134]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id 02AC320878 for ; Mon, 26 Oct 2020 08:21:10 +0000 (UTC) Authentication-Results: mail.kernel.org; dkim=pass (2048-bit key) header.d=lists.infradead.org header.i=@lists.infradead.org header.b="XNMjWAO4"; dkim=fail reason="signature verification failed" (1024-bit key) header.d=mediatek.com header.i=@mediatek.com header.b="jm00NxZS" DMARC-Filter: OpenDMARC Filter v1.3.2 mail.kernel.org 02AC320878 Authentication-Results: mail.kernel.org; dmarc=fail (p=none dis=none) header.from=mediatek.com Authentication-Results: mail.kernel.org; spf=none smtp.mailfrom=linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=merlin.20170209; h=Sender:Content-Transfer-Encoding: Content-Type:Cc:List-Subscribe:List-Help:List-Post:List-Archive: List-Unsubscribe:List-Id:MIME-Version:References:In-Reply-To:Message-ID:Date: Subject:To:From:Reply-To:Content-ID:Content-Description:Resent-Date: Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID:List-Owner; bh=0mFqOt4QDXlfhH5J1cn/wmcBRLE++fpHD5UHSa1cVfw=; b=XNMjWAO4eUaDbt7M2BOqjvr+0 aDJltolS4HvAIBRAmGZjNJ6DjEj4CmuoVkxyBIgS9NRbKPcxMJX9PWt6sfvcw3lriNc7dtPT2L+vs 2dVFTbC3T01T0Ofv53YckywzgXDcs5TcGpznPz2dRW0+XHJLCtkUp0ho3/mRet9N6h8ZP/CZ86H8C UcN3F0MQJulLUQxjwQqNHW1xE8Spa3TdIhmvQfka9UErN45OHvVFB8H9YGNSDuROUz2mWJe/3/Sys B305hwOptez4i5e5cGmtRdvt/xO6GRFUhWEjf+3t3hqCnvRFXo8lSbZV2huZm/2xyYCmfJBxo5XJK 9FDlQwQVg==; Received: from localhost ([::1] helo=merlin.infradead.org) by merlin.infradead.org with esmtp (Exim 4.92.3 #3 (Red Hat Linux)) id 1kWxjG-0006oz-NE; Mon, 26 Oct 2020 08:19:46 +0000 Received: from mailgw02.mediatek.com ([216.200.240.185]) by merlin.infradead.org with esmtps (Exim 4.92.3 #3 (Red Hat Linux)) id 1kWxit-0006gi-W9; Mon, 26 Oct 2020 08:19:25 +0000 X-UUID: 3201fda57fe846d2aa5cbf0c8f9ac692-20201026 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=mediatek.com; s=dk; h=Content-Transfer-Encoding:Content-Type:MIME-Version:References:In-Reply-To:Message-ID:Date:Subject:CC:To:From; bh=s89f08KvBYl1d0htgXzsoi2iHSJgKoDYNXWWA86n02U=; b=jm00NxZS9vVSeZArMqOgaEXsPcCPAe6Rv14yWJf/tCDCOoP2WaXbHg38B7EjRt29XxX+UqRWHyGP75Iiev8PQumVDe7CcLqBpliN7NeTaSM3L4VbldKAUQqe7ZMglKyyKBJWJg9j0IvZqvxmFSuWYRDgWyhF56YY8/NHqd4ATEI=; X-UUID: 3201fda57fe846d2aa5cbf0c8f9ac692-20201026 Received: from mtkcas66.mediatek.inc [(172.29.193.44)] by mailgw02.mediatek.com (envelope-from ) (musrelay.mediatek.com ESMTP with TLSv1.2 ECDHE-RSA-AES256-SHA384 256/256) with ESMTP id 1733819593; Mon, 26 Oct 2020 00:19:17 -0800 Received: from MTKMBS07N2.mediatek.inc (172.21.101.141) by MTKMBS62DR.mediatek.inc (172.29.94.18) with Microsoft SMTP Server (TLS) id 15.0.1497.2; Mon, 26 Oct 2020 01:19:16 -0700 Received: from mtkcas08.mediatek.inc (172.21.101.126) by mtkmbs07n2.mediatek.inc (172.21.101.141) with Microsoft SMTP Server (TLS) id 15.0.1497.2; Mon, 26 Oct 2020 16:19:14 +0800 Received: from mtkswgap22.mediatek.inc (172.21.77.33) by mtkcas08.mediatek.inc (172.21.101.73) with Microsoft SMTP Server id 15.0.1497.2 via Frontend Transport; Mon, 26 Oct 2020 16:19:13 +0800 From: Hector Yuan To: , , , "Rob Herring" , Sudeep Holla , "Rafael J. Wysocki" , Viresh Kumar , "Maxime Ripard" , Santosh Shilimkar , "Amit Kucheria" , Stephen Boyd , "Ulf Hansson" , Dave Gerlach , "Florian Fainelli" , Robin Murphy , "Lorenzo Pieralisi" , Subject: [PATCH v8 1/3] cpufreq: mediatek-hw: Add support for CPUFREQ HW Date: Mon, 26 Oct 2020 16:19:07 +0800 Message-ID: <1603700349-5922-2-git-send-email-hector.yuan@mediatek.com> X-Mailer: git-send-email 1.7.9.5 In-Reply-To: <1603700349-5922-1-git-send-email-hector.yuan@mediatek.com> References: <1603700349-5922-1-git-send-email-hector.yuan@mediatek.com> MIME-Version: 1.0 X-MTK: N X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20201026_041924_322375_6D03009C X-CRM114-Status: GOOD ( 27.88 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: hector.yuan@mediatek.com, linux-kernel@vger.kernel.org, wsd_upstream@mediatek.com Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org From: "Hector.Yuan" Add cpufreq HW support. Signed-off-by: Hector.Yuan --- drivers/cpufreq/Kconfig.arm | 12 ++ drivers/cpufreq/Makefile | 1 + drivers/cpufreq/mediatek-cpufreq-hw.c | 343 +++++++++++++++++++++++++++++++++ 3 files changed, 356 insertions(+) create mode 100644 drivers/cpufreq/mediatek-cpufreq-hw.c diff --git a/drivers/cpufreq/Kconfig.arm b/drivers/cpufreq/Kconfig.arm index cb72fb5..b9d17c5 100644 --- a/drivers/cpufreq/Kconfig.arm +++ b/drivers/cpufreq/Kconfig.arm @@ -123,6 +123,18 @@ config ARM_MEDIATEK_CPUFREQ help This adds the CPUFreq driver support for MediaTek SoCs. +config ARM_MEDIATEK_CPUFREQ_HW + tristate "MediaTek CPUFreq HW driver" + depends on ARCH_MEDIATEK || COMPILE_TEST + default m + help + Support for the CPUFreq HW driver. + Some MediaTek chipsets have a HW engine to offload the steps + necessary for changing the frequency of the CPUs. Firmware loaded + in this engine exposes a programming interface to the OS. + The driver implements the cpufreq interface for this HW engine. + Say Y if you want to support CPUFreq HW. + config ARM_OMAP2PLUS_CPUFREQ bool "TI OMAP2+" depends on ARCH_OMAP2PLUS diff --git a/drivers/cpufreq/Makefile b/drivers/cpufreq/Makefile index f1b7e3d..ffc61cd 100644 --- a/drivers/cpufreq/Makefile +++ b/drivers/cpufreq/Makefile @@ -57,6 +57,7 @@ obj-$(CONFIG_ARM_IMX6Q_CPUFREQ) += imx6q-cpufreq.o obj-$(CONFIG_ARM_IMX_CPUFREQ_DT) += imx-cpufreq-dt.o obj-$(CONFIG_ARM_KIRKWOOD_CPUFREQ) += kirkwood-cpufreq.o obj-$(CONFIG_ARM_MEDIATEK_CPUFREQ) += mediatek-cpufreq.o +obj-$(CONFIG_ARM_MEDIATEK_CPUFREQ_HW) += mediatek-cpufreq-hw.o obj-$(CONFIG_MACH_MVEBU_V7) += mvebu-cpufreq.o obj-$(CONFIG_ARM_OMAP2PLUS_CPUFREQ) += omap-cpufreq.o obj-$(CONFIG_ARM_PXA2xx_CPUFREQ) += pxa2xx-cpufreq.o diff --git a/drivers/cpufreq/mediatek-cpufreq-hw.c b/drivers/cpufreq/mediatek-cpufreq-hw.c new file mode 100644 index 0000000..3af36b0 --- /dev/null +++ b/drivers/cpufreq/mediatek-cpufreq-hw.c @@ -0,0 +1,343 @@ +// SPDX-License-Identifier: GPL-2.0 +/* + * Copyright (c) 2020 MediaTek Inc. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define LUT_MAX_ENTRIES 32U +#define LUT_FREQ GENMASK(11, 0) +#define LUT_ROW_SIZE 0x4 +#define CPUFREQ_HW_STATUS BIT(0) +#define SVS_HW_STATUS BIT(1) +#define POLL_USEC 1000 +#define TIMEOUT_USEC 300000 + +enum { + REG_FREQ_LUT_TABLE, + REG_FREQ_ENABLE, + REG_FREQ_PERF_STATE, + REG_FREQ_HW_STATE, + REG_EM_POWER_TBL, + + REG_ARRAY_SIZE, +}; + +struct cpufreq_mtk { + struct cpufreq_frequency_table *table; + void __iomem *reg_bases[REG_ARRAY_SIZE]; + int nr_opp; + cpumask_t related_cpus; +}; + +static const u16 cpufreq_mtk_offsets[REG_ARRAY_SIZE] = { + [REG_FREQ_LUT_TABLE] = 0x0, + [REG_FREQ_ENABLE] = 0x84, + [REG_FREQ_PERF_STATE] = 0x88, + [REG_FREQ_HW_STATE] = 0x8c, + [REG_EM_POWER_TBL] = 0x3D0, +}; + +static struct cpufreq_mtk *mtk_freq_domain_map[NR_CPUS]; + +static int mtk_cpufreq_get_cpu_power(unsigned long *mW, + unsigned long *KHz, struct device *cpu_dev) +{ + struct cpufreq_mtk *c = mtk_freq_domain_map[cpu_dev->id]; + int i; + + for (i = 0; i < c->nr_opp; i++) { + if (c->table[i].frequency < *KHz) + break; + } + i--; + + *KHz = c->table[i].frequency; + *mW = readl_relaxed(c->reg_bases[REG_EM_POWER_TBL] + + i * LUT_ROW_SIZE) / 1000; + + return 0; +} + +static int mtk_cpufreq_hw_target_index(struct cpufreq_policy *policy, + unsigned int index) +{ + struct cpufreq_mtk *c = policy->driver_data; + + writel_relaxed(index, c->reg_bases[REG_FREQ_PERF_STATE]); + + return 0; +} + +static unsigned int mtk_cpufreq_hw_get(unsigned int cpu) +{ + struct cpufreq_mtk *c; + unsigned int index; + + c = mtk_freq_domain_map[cpu]; + + index = readl_relaxed(c->reg_bases[REG_FREQ_PERF_STATE]); + index = min(index, LUT_MAX_ENTRIES - 1); + + return c->table[index].frequency; +} + +static int mtk_cpufreq_hw_cpu_init(struct cpufreq_policy *policy) +{ + struct cpufreq_mtk *c; + struct device *cpu_dev; + struct em_data_callback em_cb = EM_DATA_CB(mtk_cpufreq_get_cpu_power); + struct pm_qos_request *qos_request; + int sig, pwr_hw = CPUFREQ_HW_STATUS | SVS_HW_STATUS; + + qos_request = kzalloc(sizeof(*qos_request), GFP_KERNEL); + if (!qos_request) + return -ENOMEM; + + cpu_dev = get_cpu_device(policy->cpu); + if (!cpu_dev) { + pr_err("failed to get cpu%d device\n", policy->cpu); + return -ENODEV; + } + + c = mtk_freq_domain_map[policy->cpu]; + if (!c) { + pr_err("No scaling support for CPU%d\n", policy->cpu); + return -ENODEV; + } + + cpumask_copy(policy->cpus, &c->related_cpus); + + policy->freq_table = c->table; + policy->driver_data = c; + + /* Let CPUs leave idle-off state for SVS CPU initializing */ + cpu_latency_qos_add_request(qos_request, 0); + + /* HW should be in enabled state to proceed now */ + writel_relaxed(0x1, c->reg_bases[REG_FREQ_ENABLE]); + + if (readl_poll_timeout(c->reg_bases[REG_FREQ_HW_STATE], sig, + (sig & pwr_hw) == pwr_hw, POLL_USEC, + TIMEOUT_USEC)) { + if (!(sig & CPUFREQ_HW_STATUS)) { + pr_info("cpufreq hardware of CPU%d is not enabled\n", + policy->cpu); + return -ENODEV; + } + + pr_info("SVS of CPU%d is not enabled\n", policy->cpu); + } + + em_dev_register_perf_domain(cpu_dev, c->nr_opp, &em_cb, policy->cpus); + + cpu_latency_qos_remove_request(qos_request); + kfree(qos_request); + + return 0; +} + +static int mtk_cpufreq_hw_cpu_exit(struct cpufreq_policy *policy) +{ + struct cpufreq_mtk *c; + + c = mtk_freq_domain_map[policy->cpu]; + if (!c) { + pr_err("No scaling support for CPU%d\n", policy->cpu); + return -ENODEV; + } + + /* HW should be in paused state now */ + writel_relaxed(0x0, c->reg_bases[REG_FREQ_ENABLE]); + + return 0; +} + +static struct cpufreq_driver cpufreq_mtk_hw_driver = { + .flags = CPUFREQ_STICKY | CPUFREQ_NEED_INITIAL_FREQ_CHECK | + CPUFREQ_HAVE_GOVERNOR_PER_POLICY | + CPUFREQ_IS_COOLING_DEV, + .verify = cpufreq_generic_frequency_table_verify, + .target_index = mtk_cpufreq_hw_target_index, + .get = mtk_cpufreq_hw_get, + .init = mtk_cpufreq_hw_cpu_init, + .exit = mtk_cpufreq_hw_cpu_exit, + .name = "mtk-cpufreq-hw", + .attr = cpufreq_generic_attr, +}; + +static int mtk_cpu_create_freq_table(struct platform_device *pdev, + struct cpufreq_mtk *c) +{ + struct device *dev = &pdev->dev; + void __iomem *base_table; + u32 data, i, freq, prev_freq = 0; + + c->table = devm_kcalloc(dev, LUT_MAX_ENTRIES + 1, + sizeof(*c->table), GFP_KERNEL); + if (!c->table) + return -ENOMEM; + + base_table = c->reg_bases[REG_FREQ_LUT_TABLE]; + + for (i = 0; i < LUT_MAX_ENTRIES; i++) { + data = readl_relaxed(base_table + (i * LUT_ROW_SIZE)); + freq = FIELD_GET(LUT_FREQ, data) * 1000; + + if (freq == prev_freq) + break; + + c->table[i].frequency = freq; + + dev_dbg(dev, "index=%d freq=%d\n", + i, c->table[i].frequency); + + prev_freq = freq; + } + + c->table[i].frequency = CPUFREQ_TABLE_END; + c->nr_opp = i; + + return 0; +} + +static int mtk_get_related_cpus(int index, struct cpufreq_mtk *c) +{ + struct device_node *cpu_np; + struct of_phandle_args args; + int cpu, ret; + + for_each_possible_cpu(cpu) { + cpu_np = of_cpu_device_node_get(cpu); + if (!cpu_np) + continue; + + ret = of_parse_phandle_with_args(cpu_np, "mediatek,freq-domain", + "#freq-domain-cells", 0, + &args); + of_node_put(cpu_np); + if (ret < 0) + continue; + + if (index == args.args[0]) { + cpumask_set_cpu(cpu, &c->related_cpus); + mtk_freq_domain_map[cpu] = c; + } + } + + return 0; +} + +static int mtk_cpu_resources_init(struct platform_device *pdev, + unsigned int cpu, int index, + const u16 *offsets) +{ + struct cpufreq_mtk *c; + struct device *dev = &pdev->dev; + int ret, i; + void __iomem *base; + + if (mtk_freq_domain_map[cpu]) + return 0; + + c = devm_kzalloc(dev, sizeof(*c), GFP_KERNEL); + if (!c) + return -ENOMEM; + + base = devm_platform_ioremap_resource(pdev, index); + if (IS_ERR(base)) + return PTR_ERR(base); + + for (i = REG_FREQ_LUT_TABLE; i < REG_ARRAY_SIZE; i++) + c->reg_bases[i] = base + offsets[i]; + + ret = mtk_get_related_cpus(index, c); + if (ret) { + dev_err(dev, "Domain-%d failed to get related CPUs\n", index); + return ret; + } + + ret = mtk_cpu_create_freq_table(pdev, c); + if (ret) { + dev_err(dev, "Domain-%d failed to create freq table\n", index); + return ret; + } + + return 0; +} + +static int mtk_cpufreq_hw_driver_probe(struct platform_device *pdev) +{ + struct device_node *cpu_np; + struct of_phandle_args args; + const u16 *offsets; + unsigned int cpu; + int ret; + + offsets = of_device_get_match_data(&pdev->dev); + if (!offsets) + return -EINVAL; + + for_each_possible_cpu(cpu) { + cpu_np = of_cpu_device_node_get(cpu); + if (!cpu_np) { + dev_err(&pdev->dev, "Failed to get cpu %d device\n", + cpu); + return -ENODEV; + } + + ret = of_parse_phandle_with_args(cpu_np, "mediatek,freq-domain", + "#freq-domain-cells", 0, + &args); + if (ret < 0) + return ret; + + /* Get the bases of cpufreq for domains */ + ret = mtk_cpu_resources_init(pdev, cpu, args.args[0], offsets); + if (ret) { + dev_err(&pdev->dev, "CPUFreq resource init failed\n"); + return ret; + } + } + + ret = cpufreq_register_driver(&cpufreq_mtk_hw_driver); + if (ret) { + dev_err(&pdev->dev, "CPUFreq HW driver failed to register\n"); + return ret; + } + + return 0; +} + +static int mtk_cpufreq_hw_driver_remove(struct platform_device *pdev) +{ + return cpufreq_unregister_driver(&cpufreq_mtk_hw_driver); +} + +static const struct of_device_id mtk_cpufreq_hw_match[] = { + { .compatible = "mediatek,cpufreq-hw", .data = &cpufreq_mtk_offsets }, + {} +}; + +static struct platform_driver mtk_cpufreq_hw_driver = { + .probe = mtk_cpufreq_hw_driver_probe, + .remove = mtk_cpufreq_hw_driver_remove, + .driver = { + .name = "mtk-cpufreq-hw", + .of_match_table = mtk_cpufreq_hw_match, + }, +}; +module_platform_driver(mtk_cpufreq_hw_driver); + +MODULE_DESCRIPTION("Mediatek cpufreq-hw driver"); +MODULE_LICENSE("GPL v2"); -- 1.7.9.5 _______________________________________________ linux-arm-kernel mailing list linux-arm-kernel@lists.infradead.org http://lists.infradead.org/mailman/listinfo/linux-arm-kernel